// Copyright (c) 2025 Nikolai Papin // // This file is part of Easywish // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, or // (at your option) any later version. // // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See // the GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program. If not, see . package minioclient import ( "context" "fmt" "slices" "github.com/minio/minio-go/v7" "github.com/minio/minio-go/v7/pkg/lifecycle" ) var Buckets map[string]string func setupBuckets(client *minio.Client) { Buckets = map[string]string{ "avatars": "ew-avatars", "images": "ew-images", "uploads": "ew-uploads", } hiddenBuckets := []string{ "uploads", } // NOTICE: it has a formatting value in there for the bucket name!! // I'm kind of ashamed for doing this, but the library did not have // an API for configuring a policy, so we're left with JSON I guess readOnlyPolicyTemplate := `{"Version": "2012-10-17","Statement": [{"Action": ["s3:GetObject"],"Effect": "Allow","Principal": {"AWS": ["*"]},"Resource": ["arn:aws:s3:::%s/*"],"Sid": ""}]}` ctx := context.Background() var newBuckets []string for key, value := range Buckets { bucketExists, err := client.BucketExists(ctx, value); if err != nil { panic("Failure to check if bucket '" + value + "' exists: " + err.Error()) } if !bucketExists { err := client.MakeBucket(ctx, value, minio.MakeBucketOptions{}); if err != nil { panic("Failure to create bucket '" + value + "': " + err.Error()) } newBuckets = append(newBuckets, key) if !slices.Contains(hiddenBuckets, key) { client.SetBucketPolicy(ctx, value, fmt.Sprintf(readOnlyPolicyTemplate, value)) } } } if slices.Contains(newBuckets, "uploads") { uploadsCfg := lifecycle.NewConfiguration() uploadsCfg.Rules = []lifecycle.Rule{ { ID: "expire-uploads", Status: "Enabled", Expiration: lifecycle.Expiration{Days: 1}, }, } err := client.SetBucketLifecycle(ctx, Buckets["uploads"], uploadsCfg); if err != nil { errRm := client.RemoveBucket(ctx, Buckets["uploads"]) if errRm != nil { panic("Failed to set lifecycle configuration for the uploads bucket: '" + err.Error() + "' and then failed to delete it: " + errRm.Error()) } panic("Failed to set lifecycle configuration for the uploads bucket: " + err.Error()) } } }