nworks_drive_upload
Upload files to LINE WORKS drive using base64 content or local file paths. Supports user-specific folders and optional overwrite functionality.
Instructions
파일을 드라이브에 업로드합니다 (User OAuth file scope 필요). content(base64)와 fileName으로 전달하거나, filePath로 로컬 파일 경로를 지정합니다. MCP 클라이언트에서는 content+fileName 방식을 권장합니다.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| content | No | 업로드할 파일 내용 (base64 인코딩). filePath 대신 사용 | |
| fileName | No | 파일명 (content 사용 시 필수) | |
| filePath | No | 업로드할 로컬 파일 경로 (content 대신 사용, 로컬 환경에서만 동작) | |
| userId | No | 대상 사용자 ID (미지정 시 me) | |
| folderId | No | 업로드할 폴더 ID (미지정 시 루트) | |
| overwrite | No | 동일 파일명 덮어쓰기 (기본: false) |
Implementation Reference
- src/mcp/tools.ts:403-441 (handler)Handler implementation for nworks_drive_upload tool in MCP. It uses driveApi to upload files from either base64 content or a local path.
async ({ content, fileName, filePath, userId, folderId, overwrite }) => { try { let result: driveApi.UploadResult; if (content && fileName) { // MCP 방식: base64 content를 직접 받아서 업로드 const buffer = Buffer.from(content, "base64"); if (process.env["NWORKS_VERBOSE"] === "1") { console.error(`[nworks] MCP upload: fileName=${fileName}, bufferSize=${buffer.length}`); } result = await driveApi.uploadBuffer( buffer, fileName, userId ?? "me", folderId, overwrite ?? false ); } else if (filePath) { // 로컬 파일 경로 방식 const safePath = validateLocalPath(filePath); if (process.env["NWORKS_VERBOSE"] === "1") { console.error(`[nworks] MCP upload: filePath=${safePath}`); } result = await driveApi.uploadFile( safePath, userId ?? "me", folderId, overwrite ?? false ); } else { return { content: [{ type: "text" as const, text: JSON.stringify({ error: true, message: "content+fileName 또는 filePath 중 하나를 지정해야 합니다. MCP 클라이언트에서는 파일 내용을 base64로 인코딩하여 content 파라미터에 전달하고, fileName에 파일명을 지정하세요." }) }], isError: true, }; } return { content: [{ type: "text" as const, text: JSON.stringify({ success: true, ...result }) }], }; - src/mcp/tools.ts:392-402 (registration)Tool registration for nworks_drive_upload in src/mcp/tools.ts.
server.tool( "nworks_drive_upload", "파일을 드라이브에 업로드합니다 (User OAuth file scope 필요). content(base64)와 fileName으로 전달하거나, filePath로 로컬 파일 경로를 지정합니다. MCP 클라이언트에서는 content+fileName 방식을 권장합니다.", { content: z.string().optional().describe("업로드할 파일 내용 (base64 인코딩). filePath 대신 사용"), fileName: z.string().optional().describe("파일명 (content 사용 시 필수)"), filePath: z.string().optional().describe("업로드할 로컬 파일 경로 (content 대신 사용, 로컬 환경에서만 동작)"), userId: z.string().optional().describe("대상 사용자 ID (미지정 시 me)"), folderId: z.string().optional().describe("업로드할 폴더 ID (미지정 시 루트)"), overwrite: z.boolean().optional().describe("동일 파일명 덮어쓰기 (기본: false)"), }, - src/api/drive.ts:171-235 (helper)Underlying API implementation (uploadBuffer) called by the MCP tool handler.
export async function uploadBuffer( fileBuffer: Buffer, fileName: string, userId = "me", folderId?: string, overwrite = false, profile = "default" ): Promise<UploadResult> { const fileSize = fileBuffer.length; if (fileSize > MAX_UPLOAD_SIZE) { throw new ApiError("FILE_TOO_LARGE", `File size (${fileSize} bytes) exceeds maximum allowed (${MAX_UPLOAD_SIZE} bytes)`, 413); } const base = `${BASE_URL}/users/${sanitizePathSegment(userId)}/drive/files`; const createUrl = folderId ? `${base}/${sanitizePathSegment(folderId)}` : base; if (process.env["NWORKS_VERBOSE"] === "1") { console.error(`[nworks] POST ${createUrl} (create upload URL for buffer)`); } const createRes = await authedFetch( createUrl, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ fileName, fileSize, overwrite }), }, profile ); if (!createRes.ok) return handleError(createRes); const { uploadUrl } = (await createRes.json()) as UploadUrlResult; validateRedirectUrl(uploadUrl, ALLOWED_HOSTS); const boundary = `----nworks${Date.now()}`; const header = Buffer.from( `--${boundary}\r\n` + `Content-Disposition: form-data; name="Filedata"; filename="${sanitizeFileName(fileName)}"\r\n` + `Content-Type: application/octet-stream\r\n\r\n` ); const footer = Buffer.from(`\r\n--${boundary}--\r\n`); const body = Buffer.concat([header, fileBuffer, footer]); if (process.env["NWORKS_VERBOSE"] === "1") { console.error(`[nworks] POST ${uploadUrl} (upload buffer, ${fileSize} bytes)`); } const uploadRes = await authedFetch( uploadUrl, { method: "POST", headers: { "Content-Type": `multipart/form-data; boundary=${boundary}` }, body, }, profile ); if (!uploadRes.ok) return handleError(uploadRes); return (await uploadRes.json()) as UploadResult; } export async function downloadFile(