Skip to content

fix(infra): replace MinIO with RustFS for local and test object storage - #1390

Merged
iammukeshm merged 1 commit into
mainfrom
fix/replace-minio-with-rustfs
Sep 25, 2026
Merged

iammukeshm merged 1 commit into
mainfrom
fix/replace-minio-with-rustfs

Conversation

@iammukeshm

Copy link
Copy Markdown
Member

Problem

MinIO images can no longer be pulled anonymously:

On main that breaks every Testcontainers integration test, the Aspire AppHost and the docker-compose deployment on any machine without a cached image.

Fix: RustFS (rustfs/rustfs:1.0.0, S3-compatible, Apache-2.0)

Area Change
Integration tests (both factories) Generic Testcontainers container on rustfs/rustfs:1.0.0, waits on /health. Drops Testcontainers.Minio for the base Testcontainers package.
AppHost rustfs container (S3 API 9000, console 9001), RUSTFS_CORS_ALLOWED_ORIGINS for both dev origins. Bucket bootstrap moves from minio/mc to amazon/aws-cli:2.37.3 (create + public-read GetObject policy, same as the old mc anonymous set download).
Compose rustfs + rustfs-init services; healthcheck via /health.
fsh CLI Generates the new env keys in deploy/docker/.env.
Docs / rules README, AGENTS.md, .agents/rules, client READMEs, comments. src/BuildingBlocks untouched.

Breaking (compose users)

  • MINIO_ROOT_USER / MINIO_ROOT_PASSWORD → RUSTFS_ACCESS_KEY / RUSTFS_SECRET_KEY.
  • Volume minio_data → rustfs_data; service minio → rustfs. Existing objects must be copied across (e.g. aws s3 sync).
  • AppHost parameters minio-user/minio-password → rustfs-user/rustfs-password (defaults work with no secrets set).

Verification

  • dotnet build src/FSH.Starter.slnx: 0 warnings, 0 errors.
  • Integration.Tests: 746 passed, 1 skipped (pre-existing), 0 failed. Integration.Middleware.Tests: 5/5.
  • AppHost boots: rustfs-init exits 0; anonymous list → 403, anonymous object read allowed by policy, CORS preflight from :5174 → allowed; API up.
  • Compose: docker compose config valid; rustfs healthy, rustfs-init exits 0 and is idempotent on re-run.

Supersedes #1388.

🤖 Generated with Claude Code

MinIO images are no longer pullable: minio/minio and minio/mc were removed
from Docker Hub, and quay.io/minio/* now refuses anonymous pulls. That broke
every Testcontainers integration test, the Aspire AppHost and the compose
deployment on a clean machine.

- Tests: generic Testcontainers container on rustfs/rustfs:1.0.0 (drops
  Testcontainers.Minio for the base Testcontainers package).
- AppHost: RustFS container with CORS for both dev origins; bucket bootstrap
  moves from minio/mc to amazon/aws-cli (create + public-read GetObject policy).
- Compose: rustfs + rustfs-init services; MINIO_ROOT_USER/PASSWORD become
  RUSTFS_ACCESS_KEY/RUSTFS_SECRET_KEY; volume minio_data -> rustfs_data.
- fsh CLI generates the new env keys; docs/rules updated.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@iammukeshm
iammukeshm merged commit 7e34c31 into main Sep 25, 2026
18 checks passed
@iammukeshm
iammukeshm deleted the fix/replace-minio-with-rustfs branch September 25, 2026 01:46
marcelo-maciel added a commit to marcelo-maciel/dotnet-starter-kit that referenced this pull request Sep 25, 2026
Drops the carried SourceLink/Testcontainers bumps and the MinIO quay pin in favour of main (fullstackhero#1369, fullstackhero#1375, fullstackhero#1390). Identity keeps both Locale and the fullstackhero#1387 If-Match precondition on UpdateAsync; UserLocaleTests follows the new UserProfileService constructor.
marcelo-maciel added a commit to marcelo-maciel/dotnet-starter-kit that referenced this pull request Sep 25, 2026
Drops the carried SourceLink/Testcontainers bumps and the MinIO quay pin in favour of main (fullstackhero#1369, fullstackhero#1375, fullstackhero#1390).
marcelo-maciel added a commit to marcelo-maciel/dotnet-starter-kit that referenced this pull request Sep 25, 2026
Drops the carried SourceLink/Testcontainers bumps and the MinIO quay pin in favour of main (fullstackhero#1369, fullstackhero#1375, fullstackhero#1390). Profile settings keep the fullstackhero#1387 ETag flow with its new copy routed through t(); the topbar language switch now reads the profile with its ETag, sends If-Match, and refetches the shared profile query so the settings form never seeds from a spent tag.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant