Files
admin/docs/core-modules/file-manager/backend.md
T
2026-06-25 15:53:49 +03:00

11 KiB

File Manager Backend

The backend module exposes authenticated file operations under /file-manager. It validates requests, authorizes actions, normalizes paths, orchestrates file-manager behavior, and delegates raw storage work to a storage adapter.

Source root:

backend/app/base_modules/FileManager/

Request Flow

routes.ts
  -> controller/file_manager_controller.ts
  -> validator/*
  -> policy/file_manager_policy.ts
  -> services/file_manager_service.ts
  -> services/storage_service/storage_service_interface.ts
  -> services/storage_service/create_storage_service.ts
  -> services/storage_service/fs_storage_service.ts | services/storage_service/s3_storage_service.ts
  -> Adonis Drive

The controller should stay thin. It handles HTTP concerns: auth policy checks, request validation, path extraction, status codes, and response payload shape.

FileManagerService owns business orchestration. Storage adapters own raw persistence operations.

Routes

All routes are prefixed with /file-manager and use middleware.auth().

Method Route Controller Method Purpose
GET / index List root directory entries.
GET /* index List entries for a nested directory.
GET /files/details/* show Return file metadata and optional text preview content.
GET /files/raw/* raw Stream raw file content.
GET /search?q=value search Search entries recursively.
POST /folders createFolder Create a folder.
POST /files upload Upload a file.
POST /files/duplicate duplicate Duplicate one or more file entries.
PUT /entries/rename rename Rename or move an entry within its parent path.
DELETE /* destroy Delete an entry.

Authorization

Policy file:

policy/file_manager_policy.ts

Controller methods call policy abilities before performing work:

Ability Used By
viewList List entries, search entries.
view File details, raw file stream.
create Create folder, upload file, duplicate entries.
update Rename entry.
delete Delete entry.

When adding a new operation, add or reuse an explicit policy ability before adding service logic.

Validation

Validators live in:

validator/

Current validators:

File Purpose
list_validator.ts Validates filter, sort, order, max results, and pagination token.
create_directory_validator.ts Validates parent path and folder name.
rename_entry_validator.ts Validates source path and new name.
upload_file_validator.ts Validates upload path and file payload.
duplicate_entries_validator.ts Validates duplicate source paths.
schemas.ts Shared validation schema helpers.

Path extraction from wildcard routes goes through:

helpers/get_validated_path_from_request.ts

Keep path validation centralized. Avoid parsing wildcard paths directly in controllers or storage adapters.

Services

file_manager_service.ts

Main orchestration service.

Responsibilities:

  • List directory entries with filtering, sorting, and pagination.
  • Compose file detail responses with preview content.
  • Create directory response entries.
  • Validate and move entries.
  • Generate unique upload names.
  • Generate duplicate copy names.
  • Search entries.
  • Coordinate storage adapter calls.

path_service.ts

Shared path and filename utility service.

Responsibilities:

  • Convert client paths to storage paths.
  • Convert storage paths to client paths.
  • Join paths safely.
  • Get dirname and basename.
  • Parse file extension metadata.
  • Sanitize filenames.
  • Generate unique names.

Use this service for path behavior instead of string manipulation in feature code.

entry_list_service.ts

Applies list behavior to raw storage entries.

Responsibilities:

  • Filter entries by category.
  • Sort entries.
  • Keep folders before files.
  • Paginate entries.
  • Encode and decode pagination tokens.

Frontend list controls must stay compatible with this service's accepted filter and sort values.

file_preview_service.ts

Adds text preview content to previewable files.

Previewable text extensions are currently defined in:

services/file_preview_service.ts

If a file type needs rich frontend preview, keep the backend response small and stream raw content through /files/raw/* when possible.

entry_search_service.ts

Searches entries by path and includes matching parent folders so the frontend can display useful context.

Search receives an abort signal from the controller. Long-running search implementations should respect that signal.

Storage

Storage abstractions live in:

services/storage_service/

storage_service_interface.ts

Defines the storage adapter contract. Adapters expose raw operations:

  • List directory entries.
  • List recursive entries.
  • Check entry existence.
  • Get file metadata.
  • Read file content.
  • Stream file content.
  • Write file.
  • Create directory.
  • Move entry.
  • Delete entry.
  • Copy entry.

Services should call the interface, not a concrete adapter.

fs_storage_service.ts

Filesystem storage adapter.

Responsibilities:

  • Call the Adonis Drive filesystem disk.
  • Map filesystem objects to File Manager entries.
  • Handle file streams and metadata.
  • Create, move, copy, and delete filesystem entries.
  • Preserve filesystem directory marker behavior.

s3_storage_service.ts

S3-compatible storage adapter.

Responsibilities:

  • Call the Adonis Drive s3 disk.
  • Map S3 objects and common prefixes to File Manager entries.
  • Upload multipart files by streaming the temporary upload file into S3 with putStream.
  • Read file content and streams from S3.
  • Create folders with directory marker objects.
  • Move folders by moving every object under the folder prefix.
  • Delete files with exact object deletion and folders with folder-prefix deletion.
  • Copy file entries.

S3 has no native directories. The adapter uses the same .keep marker convention as the filesystem adapter so empty folders can exist.

Folder operations must use slash-terminated prefixes. For example, deleting test/ must not delete objects such as test123.txt.

fs_directory_marker_service.ts

Encapsulates the filesystem directory marker convention.

Current marker:

.keep

Do not duplicate marker logic outside this service. Storage adapters that need virtual folders should use this marker service behind the storage interface.

create_storage_service.ts

Storage service factory.

Current supported storage:

fs
s3

The active adapter is selected by DRIVE_DISK.

DRIVE_DISK=fs

or:

DRIVE_DISK=s3

Drive Configuration

Adonis Drive config lives in:

backend/config/drive.ts

Configured disks:

Disk Driver Purpose
fs services.fs Local development and filesystem-backed storage.
s3 services.s3 S3-compatible object storage, including local MinIO.

The S3 disk expects these environment variables:

Variable Local Docker Value Purpose
AWS_ACCESS_KEY_ID minioadmin S3 access key.
AWS_SECRET_ACCESS_KEY minioadmin S3 secret key.
AWS_REGION us-east-1 S3 region.
S3_BUCKET crux-drive Bucket used by the file manager.
S3_ENDPOINT http://minio:9000 in Docker, http://localhost:9000 outside Docker S3 API endpoint.
S3_CDN_URL http://localhost:9000/crux-drive/ Browser-facing public URL base for file URLs.

For MinIO, the S3 disk uses path-style addressing:

forcePathStyle: true;

The adapter also disables ACL API calls:

supportsACL: false;

Bucket public-read behavior is handled by the Docker bucket setup container.

Local S3 Simulation

Local S3 is simulated with MinIO in:

docker-compose.yml

Services:

Service Purpose
minio Runs the S3-compatible object storage server.
minio_create_bucket One-shot setup container that creates the bucket and enables anonymous download access.

MinIO console:

http://localhost:9001

Default local credentials:

user: minioadmin
pass: minioadmin

The minio_create_bucket container is expected to exit after setup. A stopped container with successful bucket logs is normal.

To rebuild after dependency or Dockerfile changes:

docker compose build --no-cache
docker compose up

Response Shape

Directory and file operations return Entry objects:

interface EntryBase {
  name: string;
  path: string;
  updatedAt?: string;
}

interface FileEntry extends EntryBase {
  type: "file";
  size?: number;
  url: string;
}

interface FolderEntry extends EntryBase {
  type: "folder";
}

List responses include pagination metadata:

{
  data: Entry[];
  meta: {
    nextPaginationToken: string | null;
  };
}

Backend Change Checklist

Before changing backend behavior:

  1. Confirm the policy ability for the operation.
  2. Add or update a validator for all request input.
  3. Keep client paths and storage paths separated through path_service.ts.
  4. Update the frontend DTO or mapper if response shape changes.
  5. Update this documentation when routes, permissions, storage contracts, or response shapes change.