Build & Deploy / build-and-push (backend) (push) Failing after 35s
Build & Deploy / build-and-push (discord-gateway) (push) Failing after 25s
Build & Deploy / build-and-push (proxy) (push) Failing after 25s
- Remove pnpm workspace, moon repo, and all monorepo tooling - Delete packages/shared/, embed shared code directly into each service - Copy packages/shared/src/* -> services/backend/src/shared/ and services/discord-gateway/src/shared/ - Replace all @bete/shared imports with @/shared/ path alias - Remove @bete/shared workspace dependency from both services - Update root package.json scripts from --filter to --prefix - Rewrite Dockerfiles to build each service standalone - Clean up biome.json, .gitignore, remove root drizzle.config.ts
81 lines
1.9 KiB
TypeScript
81 lines
1.9 KiB
TypeScript
import { createChildLogger } from "@/shared/logger/index";
|
|
import { retryWithBackoff } from "@/shared/utils/index";
|
|
|
|
const logger = createChildLogger("tele-upload");
|
|
|
|
export interface TeleUploadResponse {
|
|
download_url: string;
|
|
public_id?: string;
|
|
file_name?: string;
|
|
size_bytes?: number;
|
|
}
|
|
|
|
export interface TeleUploadResult {
|
|
url: string;
|
|
publicId?: string;
|
|
filename?: string;
|
|
sizeBytes?: number;
|
|
}
|
|
|
|
export function parseTeleUploadResponse(
|
|
response: TeleUploadResponse,
|
|
): TeleUploadResult {
|
|
if (!response.download_url) {
|
|
throw new Error("Missing download_url in response");
|
|
}
|
|
|
|
return {
|
|
url: response.download_url,
|
|
publicId: response.public_id,
|
|
filename: response.file_name,
|
|
sizeBytes: response.size_bytes,
|
|
};
|
|
}
|
|
|
|
export async function uploadToTele(input: {
|
|
buffer: Buffer;
|
|
filename: string;
|
|
contentType: string;
|
|
uploadUrl: string;
|
|
timeoutMs?: number;
|
|
retries: number;
|
|
}): Promise<TeleUploadResult> {
|
|
const { buffer, filename, contentType, uploadUrl, timeoutMs, retries } =
|
|
input;
|
|
|
|
logger.debug({ filename, uploadUrl }, "Starting tele upload");
|
|
|
|
const response = await retryWithBackoff(
|
|
async () => {
|
|
const fileBlob = new Blob([new Uint8Array(buffer)], {
|
|
type: contentType,
|
|
});
|
|
const formData = new FormData();
|
|
formData.append("file", fileBlob, filename);
|
|
formData.append("fileName", filename);
|
|
|
|
const res = await fetch(uploadUrl, {
|
|
method: "POST",
|
|
headers: {
|
|
accept: "application/json",
|
|
},
|
|
body: formData,
|
|
...(timeoutMs ? { signal: AbortSignal.timeout(timeoutMs) } : {}),
|
|
});
|
|
|
|
if (!res.ok) {
|
|
throw new Error(`Upload failed: Status ${res.status}`);
|
|
}
|
|
|
|
return (await res.json()) as TeleUploadResponse;
|
|
},
|
|
{
|
|
retries,
|
|
minTimeout: 1000,
|
|
maxTimeout: 10000,
|
|
},
|
|
);
|
|
|
|
return parseTeleUploadResponse(response);
|
|
}
|