feat(api): per-instance file bridge — list/read/write via the new agent file manager
GET /api/instances/:id/files (list) + /file (read), PUT /file (write) —
tenant-guarded, routed through requestScoped to the per-instance
corrosion.{license}.{instance}.files.cmd using the new agent's {op,path}
protocol (jailed to the instance root, symlink-safe). files.view /
files.manage perms. Foundation for the per-game config editor and for
fixing the legacy VueFinder File Manager (which still speaks the retired
Go fm_* protocol on the wrong subject and is broken under per-license
auth — separate reconciliation).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
import { Controller, Post, Body, Param } from '@nestjs/common';
|
||||
import { Controller, Post, Get, Put, Body, Param, Query } from '@nestjs/common';
|
||||
import { ApiTags, ApiBearerAuth, ApiOperation } from '@nestjs/swagger';
|
||||
import { CurrentTenant } from '../../common/decorators/current-tenant.decorator';
|
||||
import { RequirePermission } from '../../common/decorators/require-permission.decorator';
|
||||
@@ -31,4 +31,37 @@ export class InstancesController {
|
||||
) {
|
||||
return this.instances.rcon(licenseId, id, body.command);
|
||||
}
|
||||
|
||||
@Get(':id/files')
|
||||
@RequirePermission('files.view')
|
||||
@ApiOperation({ summary: 'List a directory in the instance (jailed to its root)' })
|
||||
async listFiles(
|
||||
@CurrentTenant() licenseId: string,
|
||||
@Param('id') id: string,
|
||||
@Query('path') path?: string,
|
||||
) {
|
||||
return this.instances.listFiles(licenseId, id, path ?? '');
|
||||
}
|
||||
|
||||
@Get(':id/file')
|
||||
@RequirePermission('files.view')
|
||||
@ApiOperation({ summary: 'Read a text file from the instance (jailed, 5 MiB cap)' })
|
||||
async readFile(
|
||||
@CurrentTenant() licenseId: string,
|
||||
@Param('id') id: string,
|
||||
@Query('path') path: string,
|
||||
) {
|
||||
return this.instances.readFile(licenseId, id, path);
|
||||
}
|
||||
|
||||
@Put(':id/file')
|
||||
@RequirePermission('files.manage')
|
||||
@ApiOperation({ summary: 'Write a text file in the instance (jailed)' })
|
||||
async writeFile(
|
||||
@CurrentTenant() licenseId: string,
|
||||
@Param('id') id: string,
|
||||
@Body() body: { path: string; content: string },
|
||||
) {
|
||||
return this.instances.writeFile(licenseId, id, body.path, body.content ?? '');
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user