FIX - restore FiveManage camera and memo uploads (#19)

* TRY - isolate FiveManage media upload verification

* TRY - verify unindexed FiveManage storage objects

* FIX - bind FiveManage uploads by storage key

* FIX - match FiveManage camera upload flow

* FIX - match FiveManage memo upload flow
This commit is contained in:
Leon.Schmidt
2026-08-21 01:29:56 +02:00
committed by GitHub
parent 7bbafd0026
commit 7b4e445394
18 changed files with 556 additions and 154 deletions
+18 -9
View File
@@ -170,6 +170,7 @@ local function validate_upload(data)
local title_length = title and utf8.len(title) or nil
local note_length = note and utf8.len(note) or nil
local duration_ms = tonumber(data.durationMs)
local size_bytes = tonumber(data.sizeBytes)
local normalized_mime = allowed_audio_mimes[data.mimeType]
local waveform = normalize_waveform(data.waveform)
if not title_length or title_length < 1 or title_length > Config.Memos.TitleMaxLength
@@ -177,6 +178,8 @@ local function validate_upload(data)
or not duration_ms or duration_ms ~= duration_ms
or duration_ms == math.huge or duration_ms == -math.huge
or duration_ms < 300 or duration_ms > Config.Memos.MaximumDurationMs
or not size_bytes or size_bytes ~= math.floor(size_bytes)
or size_bytes < 1 or size_bytes > Config.Memos.MaximumBytes
or not normalized_mime or not waveform or type(data.pinned) ~= "boolean"
then
return nil
@@ -188,6 +191,7 @@ local function validate_upload(data)
mime_type = normalized_mime,
note = note,
pinned = data.pinned,
size_bytes = size_bytes,
title = title,
waveform = waveform,
}
@@ -373,20 +377,18 @@ RegisterNetEvent("sky_phone:memos:request-upload", function(data)
upload_result(src, memo.correlation_id, false, presigned_error)
return
end
local ids = Bridge.Database.Query("SELECT UUID() AS `request_id`, UUID() AS `capture_token`", {})
local ids = Bridge.Database.Query("SELECT UUID() AS `request_id`", {})
local request_id = ids[1] and ids[1].request_id
local capture_token = ids[1] and ids[1].capture_token
if type(request_id) ~= "string" or type(capture_token) ~= "string" then
error("[sky_phone] Database did not generate a voice memo upload token.")
if type(request_id) ~= "string" then
error("[sky_phone] Database did not generate a voice memo upload request ID.")
end
pending_uploads[request_id] = {
capture_token = capture_token,
media_type = "audio",
mime_type = memo.mime_type,
memo = memo,
owner = owner,
owner_key = pending_owner_key,
purpose = "memo",
size_bytes = memo.size_bytes,
source = src,
}
SetTimeout(Config.Memos.UploadSessionTimeoutMs, function()
@@ -395,7 +397,6 @@ RegisterNetEvent("sky_phone:memos:request-upload", function(data)
TriggerClientEvent("sky_phone:memos:upload-ready", src, {
requestId = request_id,
correlationId = memo.correlation_id,
captureToken = capture_token,
presignedUrl = presigned_url,
uploadTimeoutMs = Config.Media.FiveManage.UploadTimeoutMs,
})
@@ -412,14 +413,22 @@ RegisterNetEvent("sky_phone:memos:complete-upload", function(data)
local owner, error_response = device_owner(src, state.owner.imei)
if not owner or owner.imei ~= state.owner.imei or owner.account_id ~= state.owner.account_id then
pending_uploads[request_id] = nil
local rejected, _, trusted_remote = SkyPhoneMedia.VerifyRemoteUpload(state, data.remoteId, data.url)
local rejected, _, trusted_remote = SkyPhoneMedia.VerifyRemoteUpload(
state,
data.remoteId,
data.url
)
if rejected or trusted_remote then
discard_verified_upload(data.remoteId)
end
upload_result(src, state.memo.correlation_id, false, error_response and error_response.error or "owner_changed")
return
end
local verified, verify_error, trusted_remote = SkyPhoneMedia.VerifyRemoteUpload(state, data.remoteId, data.url)
local verified, verify_error, trusted_remote = SkyPhoneMedia.VerifyRemoteUpload(
state,
data.remoteId,
data.url
)
if not verified then
pending_uploads[request_id] = nil
if trusted_remote then