fix(vikon): store version in file instead of cache to prevent revert after TTL expiry

This commit is contained in:
F4ilji
2026-07-06 13:28:22 +05:00
parent 9f4dfd9bfc
commit 65f4220932
6 changed files with 31 additions and 43 deletions
@@ -345,7 +345,14 @@ class UpdateCoreAction
$latestVersion = $body['version'] ?? null;
if ($latestVersion) {
cache()->put('vikon:current_version', $latestVersion, 3600);
$file = config('vikon.version_file');
if ($file) {
$dir = dirname($file);
if (!is_dir($dir)) {
mkdir($dir, 0755, true);
}
file_put_contents($file, $latestVersion);
}
Log::channel('vikon')->info('Vikon: version updated', ['version' => $latestVersion]);
}
} catch (\Throwable $e) {
@@ -95,13 +95,11 @@ class VikonServiceProvider extends ServiceProvider
$this->loadRoutesFrom(app_path('Containers/VikonIntegration/UI/WEB/Routes/web.php'));
$this->app->bind('vikon.version', function () {
$cached = cache()->get('vikon:current_version');
if ($cached) {
return $cached;
$file = config('vikon.version_file');
if ($file && file_exists($file)) {
return trim(file_get_contents($file));
}
$version = config('vikon.current_version', '5.90.8.1');
cache()->put('vikon:current_version', $version, 3600);
return $version;
return config('vikon.current_version', '5.90.8.1');
});
}
}
@@ -41,6 +41,11 @@ class VikonController extends Controller
if ($isAuth && $token) {
$accessResult = $this->checkAccess->run($token);
$parts = $accessResult['parts'] ?? [];
$versionResult = $this->checkVersion->run($token);
if (!empty($versionResult['latest_version'])) {
$this->writeVersionFile($versionResult['latest_version']);
}
}
return inertia()->render('Dashboard/VikonUpdates/Index', [
@@ -85,7 +90,7 @@ class VikonController extends Controller
return inertia()->render('Dashboard/VikonUpdates/Index', [
'is_authenticated' => $isAuth,
'current_version' => config('vikon.current_version'),
'current_version' => app('vikon.version'),
'modules' => config('vikon.modules'),
'parts' => $parts,
'vikon_api_domain' => config('vikon.api_domain'),
@@ -138,16 +143,6 @@ class VikonController extends Controller
return response()->json($result);
}
public function checkVersion(): JsonResponse
{
$token = Session::get('vikon_access_token');
if (!$token) {
return response()->json(['success' => false, 'requires_auth' => true], 401);
}
return response()->json($this->checkVersion->run($token));
}
public function updateModule(UpdateModuleRequest $request): JsonResponse
{
$token = Session::get('vikon_access_token');
@@ -220,4 +215,16 @@ class VikonController extends Controller
return response()->json(['url' => $url]);
}
private function writeVersionFile(string $version): void
{
$file = config('vikon.version_file');
if ($file) {
$dir = dirname($file);
if (!is_dir($dir)) {
mkdir($dir, 0755, true);
}
file_put_contents($file, $version);
}
}
}
@@ -13,7 +13,6 @@ Route::prefix('/dashboard/vikon-updates')
Route::post('/authenticate', [VikonController::class, 'authenticate'])->name('authenticate');
Route::post('/refresh-token', [VikonController::class, 'refreshToken'])->name('refresh-token');
Route::post('/check-access', [VikonController::class, 'checkAccess'])->name('check-access');
Route::post('/check-version', [VikonController::class, 'checkVersion'])->name('check-version');
Route::post('/update-module', [VikonController::class, 'updateModule'])->name('update-module');
Route::post('/sync-files', [VikonController::class, 'syncFiles'])->name('sync-files');
Route::post('/update-part', [VikonController::class, 'updatePart'])->name('update-part');
+1
View File
@@ -11,6 +11,7 @@ return [
'filemanager_domain' => env('VIKON_FILEMANAGER_DOMAIN', 'https://file.db-nica.ru/'),
'current_version' => '5.90.8.1',
'version_file' => storage_path('app/vikon/current_version.txt'),
'http_timeout' => env('VIKON_HTTP_TIMEOUT', 60),
'http_retries' => env('VIKON_HTTP_RETRIES', 3),
@@ -31,16 +31,6 @@
<p class="text-2xl font-semibold mt-1">{{ currentVersion }}</p>
</div>
</div>
<div v-if="versionInfo.has_update" class="p-3 bg-yellow-50 border border-yellow-200 rounded-lg mt-4">
<p class="text-sm font-medium text-yellow-800">Доступно обновление: {{ versionInfo.latest_version }}</p>
</div>
<div v-else-if="versionInfo.latest_version" class="p-3 bg-green-50 border border-green-200 rounded-lg mt-4">
<p class="text-sm font-medium text-green-800">Установлена последняя версия</p>
</div>
<button @click="checkVersion" :disabled="checkingVersion"
class="mt-4 w-full px-4 py-2 bg-surface border border-layer-line rounded-lg hover:bg-muted-hover disabled:opacity-50">
{{ checkingVersion ? 'Проверка...' : 'Проверить обновления' }}
</button>
</div>
<div class="bg-layer border border-layer-line rounded-lg p-6">
@@ -183,13 +173,11 @@ function moduleName(id) { return moduleNames[id] || `Модуль ${id}`; }
const isAuthenticated = ref(props.is_authenticated);
const currentVersion = ref(props.current_version);
const checkingVersion = ref(false);
const checkingAccess = ref(false);
const updating = ref(null);
const updatingAll = ref(false);
const updatePhase = ref('');
const updateError = ref(null);
const versionInfo = ref({ current_version: props.current_version, has_update: false, latest_version: null });
const accessInfo = ref({ has_access: false, error: null });
const selectedParts = ref({});
if (props.parts) {
@@ -216,7 +204,6 @@ onMounted(() => {
}
if (isAuthenticated.value) {
checkAccess();
checkVersion();
}
});
@@ -232,16 +219,6 @@ async function checkAccess() {
}
}
async function checkVersion() {
checkingVersion.value = true;
try {
const res = await axios.post(route('dashboard.vikon-updates.check-version'));
versionInfo.value = res.data;
} finally {
checkingVersion.value = false;
}
}
async function updateModule(moduleId) {
const partsToUpdate = selectedParts.value[moduleId] || [];
const msg = partsToUpdate.length
@@ -347,7 +324,6 @@ async function logout() {
await axios.post(route('dashboard.vikon-updates.logout'));
isAuthenticated.value = false;
accessInfo.value = { has_access: false, error: null };
versionInfo.value = { current_version: currentVersion.value, has_update: false, latest_version: null };
} catch {}
}
</script>