fix handle retry button
This commit is contained in:
@@ -4,6 +4,7 @@ namespace App\Http\Controllers\Api;
|
||||
|
||||
use App\Enums\ImportDatasourceStatus;
|
||||
use App\Http\Controllers\Controller;
|
||||
use App\Jobs\RetrySyncronizeJob;
|
||||
use App\Jobs\ScrapingDataJob;
|
||||
use App\Jobs\SyncronizeSIMBG;
|
||||
use App\Models\ImportDatasource;
|
||||
@@ -37,35 +38,25 @@ class ScrapingController extends Controller
|
||||
return $this->resSuccess(["message" => "Success execute scraping service on background, check status for more"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Store a newly created resource in storage.
|
||||
*/
|
||||
public function store(Request $request)
|
||||
{
|
||||
//
|
||||
public function retry_syncjob(string $import_datasource_id){
|
||||
try{
|
||||
|
||||
$import_datasource = ImportDatasource::find($import_datasource_id);
|
||||
if(!$import_datasource){
|
||||
return $this->resError("Invalid import datasource id", null, 404);
|
||||
}
|
||||
|
||||
/**
|
||||
* Display the specified resource.
|
||||
*/
|
||||
public function show(string $id)
|
||||
{
|
||||
//
|
||||
dispatch(new RetrySyncronizeJob($import_datasource->id));
|
||||
return response()->json([
|
||||
"success" => true,
|
||||
"message" => "Retrying scrape job on background, check status for more"
|
||||
]);
|
||||
}catch(\Exception $e){
|
||||
return response()->json([
|
||||
"success" => false,
|
||||
"message" => "Failed to retry sync job",
|
||||
"error" => $e->getMessage()
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the specified resource in storage.
|
||||
*/
|
||||
public function update(Request $request, string $id)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the specified resource from storage.
|
||||
*/
|
||||
public function destroy(string $id)
|
||||
{
|
||||
//
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,6 +29,7 @@ class ImportDatasourceResource extends JsonResource
|
||||
"finish_time" => $finishTime ? $finishTime->toDateTimeString() : null,
|
||||
"created_at" => $this->created_at->toDateTimeString(),
|
||||
"updated_at" => $this->updated_at->toDateTimeString(),
|
||||
"failed_uuid" => $this->failed_uuid
|
||||
];
|
||||
}
|
||||
}
|
||||
|
||||
76
app/Jobs/RetrySyncronizeJob.php
Normal file
76
app/Jobs/RetrySyncronizeJob.php
Normal file
@@ -0,0 +1,76 @@
|
||||
<?php
|
||||
|
||||
namespace App\Jobs;
|
||||
|
||||
use App\Enums\ImportDatasourceStatus;
|
||||
use App\Models\BigdataResume;
|
||||
use App\Models\ImportDatasource;
|
||||
use Illuminate\Contracts\Queue\ShouldQueue;
|
||||
use Illuminate\Foundation\Queue\Queueable;
|
||||
use App\Services\ServiceTabPbgTask;
|
||||
use App\Services\ServiceGoogleSheet;
|
||||
use Illuminate\Foundation\Bus\Dispatchable;
|
||||
use Illuminate\Queue\InteractsWithQueue;
|
||||
use Illuminate\Queue\SerializesModels;
|
||||
class RetrySyncronizeJob implements ShouldQueue
|
||||
{
|
||||
use Queueable, Dispatchable, InteractsWithQueue, SerializesModels;
|
||||
private $import_datasource_id;
|
||||
public function __construct(int $import_datasource_id)
|
||||
{
|
||||
$this->import_datasource_id = $import_datasource_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute the job.
|
||||
*/
|
||||
public function handle(): void
|
||||
{
|
||||
try{
|
||||
$service_tab_pbg_task = app(ServiceTabPbgTask::class);
|
||||
$service_google_sheet = app(ServiceGoogleSheet::class);
|
||||
|
||||
$failed_import = ImportDatasource::find($this->import_datasource_id);
|
||||
|
||||
$failed_import->update([
|
||||
'message' => "Retrying from UUID: ". $failed_import->failed_uuid,
|
||||
'status' => ImportDatasourceStatus::Processing->value,
|
||||
'start_time' => now()
|
||||
]);
|
||||
|
||||
$current_failed_uuid = null;
|
||||
try{
|
||||
$service_tab_pbg_task->run_service($failed_import->failed_uuid);
|
||||
}catch(\Exception $e){
|
||||
$current_failed_uuid = $service_tab_pbg_task->getFailedUUID();
|
||||
throw $e;
|
||||
}
|
||||
|
||||
$data_setting_result = $service_google_sheet->get_big_resume_data();
|
||||
|
||||
BigdataResume::generateResumeData($failed_import->id, "all", $data_setting_result);
|
||||
BigdataResume::generateResumeData($failed_import->id, now()->year, $data_setting_result);
|
||||
|
||||
$failed_import->update([
|
||||
'status' => ImportDatasourceStatus::Success->value,
|
||||
'message' => "Retry completed successfully from UUID: ". $failed_import->failed_uuid,
|
||||
'finish_time' => now(),
|
||||
'failed_uuid' => null
|
||||
]);
|
||||
}catch(\Exception $e){
|
||||
\Log::error("RetrySyncronizeJob Failed: ". $e->getMessage(), [
|
||||
'exception' => $e,
|
||||
]);
|
||||
if(isset($failed_import)){
|
||||
$failed_import->update([
|
||||
'status' => ImportDatasourceStatus::Failed->value,
|
||||
'message' => "Retry failed from UUID: ". $failed_import->failed_uuid,
|
||||
'finish_time' => now(),
|
||||
'failed_uuid' => $current_failed_uuid
|
||||
]);
|
||||
}
|
||||
|
||||
$this->fail($e);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -44,13 +44,21 @@ class ScrapingDataJob implements ShouldQueue
|
||||
'message' => 'Initiating scraping...',
|
||||
'response_body' => null,
|
||||
'status' => 'processing',
|
||||
'start_time' => now()
|
||||
'start_time' => now(),
|
||||
'failed_uuid' => null
|
||||
]);
|
||||
|
||||
$failed_uuid = null;
|
||||
|
||||
// Run the scraping services
|
||||
$service_google_sheet->run_service();
|
||||
$service_pbg_task->run_service();
|
||||
try{
|
||||
$service_tab_pbg_task->run_service();
|
||||
}catch(\Exception $e){
|
||||
$failed_uuid = $service_tab_pbg_task->getFailedUUID();
|
||||
throw $e;
|
||||
}
|
||||
|
||||
$data_setting_result = $service_google_sheet->get_big_resume_data();
|
||||
|
||||
@@ -72,7 +80,8 @@ class ScrapingDataJob implements ShouldQueue
|
||||
$import_datasource->update([
|
||||
'status' => 'failed',
|
||||
'response_body' => 'Error: ' . $e->getMessage(),
|
||||
'finish_time' => now()
|
||||
'finish_time' => now(),
|
||||
'failed_uuid' => $failed_uuid,
|
||||
]);
|
||||
}
|
||||
|
||||
|
||||
@@ -158,8 +158,6 @@ class ServicePbgTask
|
||||
]);
|
||||
}
|
||||
|
||||
Log::info("Page {$currentPage} fetched & saved", ['records' => count($saved_data)]);
|
||||
|
||||
$currentPage++;
|
||||
} while ($currentPage <= $totalPage);
|
||||
|
||||
|
||||
@@ -19,6 +19,7 @@ class ServiceTabPbgTask
|
||||
private $service_token;
|
||||
private $user_token;
|
||||
private $user_refresh_token;
|
||||
protected $current_uuid = null;
|
||||
|
||||
public function __construct(Client $client, ServiceTokenSIMBG $service_token)
|
||||
{
|
||||
@@ -34,24 +35,41 @@ class ServiceTabPbgTask
|
||||
$this->user_refresh_token = $auth_data['refresh'];
|
||||
}
|
||||
|
||||
public function run_service()
|
||||
public function run_service($retry_uuid = null)
|
||||
{
|
||||
try {
|
||||
$pbg_tasks = PbgTask::all();
|
||||
$pbg_tasks = PbgTask::orderBy('id')->get();
|
||||
$start = false;
|
||||
|
||||
foreach ($pbg_tasks as $pbg_task) {
|
||||
if($retry_uuid){
|
||||
if($pbg_task->uuid === $retry_uuid){
|
||||
$start = true;
|
||||
}
|
||||
|
||||
if(!$start){
|
||||
continue;
|
||||
}
|
||||
}
|
||||
try{
|
||||
$this->current_uuid = $pbg_task->uuid;
|
||||
$this->scraping_task_assignments($pbg_task->uuid);
|
||||
$this->scraping_task_retributions($pbg_task->uuid);
|
||||
$this->scraping_task_integrations($pbg_task->uuid);
|
||||
|
||||
// Process task assignments here if needed
|
||||
Log::info("Successfully fetched for UUID: {$pbg_task->uuid}");
|
||||
}
|
||||
} catch (\Exception $e) {
|
||||
Log::error("Failed to scrape task assignments: " . $e->getMessage());
|
||||
}catch(\Exception $e){
|
||||
Log::error("Failed on UUID: {$this->current_uuid}, Error: " . $e->getMessage());
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
} catch (\Exception $e) {
|
||||
Log::error("Failed to syncronize: " . $e->getMessage());
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
|
||||
public function getFailedUUID(){
|
||||
return $this->current_uuid;
|
||||
}
|
||||
|
||||
private function scraping_task_assignments($uuid)
|
||||
{
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\Database\Migrations\Migration;
|
||||
use Illuminate\Database\Schema\Blueprint;
|
||||
use Illuminate\Support\Facades\Schema;
|
||||
|
||||
return new class extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*/
|
||||
public function up(): void
|
||||
{
|
||||
Schema::table('import_datasources', function (Blueprint $table) {
|
||||
$table->string('failed_uuid')->nullable()->after('status');
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*/
|
||||
public function down(): void
|
||||
{
|
||||
Schema::table('import_datasources', function (Blueprint $table) {
|
||||
$table->dropColumn('failed_uuid');
|
||||
});
|
||||
}
|
||||
};
|
||||
@@ -27,6 +27,7 @@ class BigdataResume {
|
||||
this.table = new Grid({
|
||||
columns: [
|
||||
{ name: "ID" },
|
||||
{ name: "Year" },
|
||||
{ name: "Jumlah Potensi" },
|
||||
{ name: "Total Potensi" },
|
||||
{ name: "Jumlah Berkas Belum Terverifikasi" },
|
||||
@@ -79,6 +80,7 @@ class BigdataResume {
|
||||
then: (data) => {
|
||||
return data.data.map((item) => [
|
||||
item.id,
|
||||
item.year,
|
||||
item.potention_count,
|
||||
addThousandSeparators(item.potention_sum),
|
||||
item.non_verified_count,
|
||||
|
||||
@@ -28,6 +28,19 @@ class SyncronizeTask {
|
||||
"Duration",
|
||||
"Finished",
|
||||
"Created",
|
||||
{
|
||||
name: "Action",
|
||||
formatter: (cell) => {
|
||||
if (cell.status === "failed") {
|
||||
return gridjs.html(`
|
||||
<button data-id="${cell.id}" class="btn btn-sm btn-warning d-flex align-items-center gap-1 btn-retry">
|
||||
<iconify-icon icon="mingcute:refresh-3-line" width="15" height="15"></iconify-icon>
|
||||
<span>Retry</span>
|
||||
</button>
|
||||
`);
|
||||
}
|
||||
},
|
||||
},
|
||||
],
|
||||
search: {
|
||||
server: {
|
||||
@@ -62,10 +75,20 @@ class SyncronizeTask {
|
||||
item.duration,
|
||||
item.finish_time,
|
||||
item.created_at,
|
||||
item,
|
||||
]),
|
||||
total: (data) => data.meta.total,
|
||||
},
|
||||
}).render(tableContainer);
|
||||
|
||||
tableContainer.addEventListener("click", (event) => {
|
||||
let btn = event.target.closest(".btn-retry");
|
||||
if (btn) {
|
||||
const id = btn.getAttribute("data-id");
|
||||
btn.disabled = true;
|
||||
this.handleRetrySync(id, btn);
|
||||
}
|
||||
});
|
||||
}
|
||||
handleSubmitSync() {
|
||||
const button = document.getElementById("btn-sync-submit");
|
||||
@@ -117,6 +140,48 @@ class SyncronizeTask {
|
||||
});
|
||||
}
|
||||
|
||||
handleRetrySync(id, btn) {
|
||||
const apiToken = document
|
||||
.querySelector('meta[name="api-token"]')
|
||||
.getAttribute("content");
|
||||
|
||||
fetch(`${GlobalConfig.apiHost}/api/retry-scraping/${id}`, {
|
||||
method: "GET",
|
||||
headers: {
|
||||
Authorization: `Bearer ${apiToken}`,
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
})
|
||||
.then(async (response) => {
|
||||
if (!response.ok) {
|
||||
throw new Error(`HTTP error! Status: ${response.status}`);
|
||||
}
|
||||
return response.json();
|
||||
})
|
||||
.then((data) => {
|
||||
console.log("API Response:", data); // Debugging
|
||||
|
||||
// Show success message
|
||||
const message =
|
||||
data?.data?.message ||
|
||||
data?.message ||
|
||||
"Synchronization successful!";
|
||||
this.toastMessage.innerText = message;
|
||||
this.toast.show();
|
||||
})
|
||||
.catch((err) => {
|
||||
console.error("Fetch error:", err);
|
||||
|
||||
// Show error message
|
||||
this.toastMessage.innerText =
|
||||
err.message ||
|
||||
"Failed to synchronize, something went wrong!";
|
||||
this.toast.show();
|
||||
|
||||
// Re-enable button on failure
|
||||
btn.disabled = false;
|
||||
});
|
||||
}
|
||||
handleSyncClick() {
|
||||
const button = document.getElementById("btn-sync-submit");
|
||||
const spinner = document.getElementById("spinner");
|
||||
|
||||
@@ -72,7 +72,11 @@ Route::group(['middleware' => 'auth:sanctum'], function (){
|
||||
});
|
||||
|
||||
// scraping
|
||||
Route::apiResource('/scraping', ScrapingController::class);
|
||||
Route::controller(ScrapingController::class)->group(function (){
|
||||
Route::get('/scraping','index')->name('scraping');
|
||||
Route::get('/retry-scraping/{id}','retry_syncjob')->name('retry-scraping');
|
||||
});
|
||||
// Route::apiResource('/scraping', ScrapingController::class);
|
||||
|
||||
// reklame
|
||||
Route::apiResource('advertisements', AdvertisementController::class);
|
||||
|
||||
Reference in New Issue
Block a user