Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 46 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
name: CI

on:
push:
branches: ["**"]
pull_request:

jobs:
build_and_push:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write # חשוב ל-GHCR

env:
IMAGE_TAG: ${{ github.sha }}

steps:
- name: Checkout
uses: actions/checkout@v4

- name: Set image name (org)
run: echo "IMAGE_NAME=ghcr.io/kamatechorg/minio-bootstrap" >> $GITHUB_ENV

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3

- name: Login to GHCR (using GITHUB_TOKEN)
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}

- name: Build & Push
uses: docker/build-push-action@v6
with:
context: ./storage/minio-bootstrap
file: ./storage/minio-bootstrap/Dockerfile
push: true
tags: |
${{ env.IMAGE_NAME }}:latest
${{ env.IMAGE_NAME }}:${{ env.IMAGE_TAG }}

- name: Validate compose
run: docker compose -f storage/docker-compose.yml config -q
56 changes: 55 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1 +1,55 @@
# AgCloud
# MinIO Tiering Demo (All-in-One Docker)

Runs HOT + COLD MinIO servers in one container, with bootstrap script that:
- Creates buckets: imagery (HOT), cold-tier (COLD)
- Enables versioning on HOT
- Defines lifecycle: move objects >7 days → COLD

## Quickstart
```bash
docker build -t minio-allinone .
docker run -d --name minio-aio -p 9000:9000 -p 9001:9001 -p 9100:9100 -p 9101:9101 minio-allinone
```

Consoles: HOT → http://localhost:9001 | COLD → http://localhost:9101

Upload test:
```bash
docker exec -it minio-aio mc cp /etc/hosts hot/imagery/test.txt
```
# MinIO Monitoring Demo (Docker Compose)

Runs MinIO with HOT + COLD endpoints, Prometheus scraping enabled, and Grafana dashboard for monitoring.

- MinIO exposes metrics on ports 9000 (HOT) and 9100 (COLD)
- Prometheus scrapes MinIO metrics from both endpoints
- Grafana shows dashboards with:
- **PUT latency (p95)**
- **Bucket size**

## Quickstart
```bash
docker compose up -d --build
```

## Consoles & UIs
- HOT MinIO Console → http://localhost:9001
- COLD MinIO Console → http://localhost:9101
- Prometheus → http://localhost:9090
- Grafana → http://localhost:3000 (admin / admin)

## Example PromQL
### PUT latency (p95)
```promql
histogram_quantile(
0.95,
sum by (le, job, instance) (
rate(minio_s3_requests_ttfb_seconds_distribution_bucket{api="putobject"}[5m])
)
)
```

### Bucket size per bucket
```promql
sum by (bucket) (minio_bucket_usage_size_bytes)
```
Binary file added monitoring/dashbaord.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
46 changes: 46 additions & 0 deletions monitoring/docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
# הערה: אפשר למחוק את ה-version בראש (היא לא נדרשת ב-compose v2)
services:
minio:
build:
context: ../storage/minio-bootstrap # <<< הנתיב לתיקייה שבה ה-Dockerfile שלך
dockerfile: Dockerfile
container_name: minio
environment:
MINIO_ROOT_USER: minio
MINIO_ROOT_PASSWORD: minio123
MINIO_PROMETHEUS_AUTH_TYPE: public
HOT_ADDRESS: ":9000"
HOT_CONSOLE: ":9001"
COLD_ADDRESS: ":9100"
COLD_CONSOLE: ":9101"
HOT_ENDPOINT: "http://127.0.0.1:9000"
COLD_ENDPOINT: "http://127.0.0.1:9100"
MC_ALIAS_HOT: "hot"
MC_ALIAS_COLD: "cold"
MC_HOST_hot: "http://minio:minio123@127.0.0.1:9000"
MC_HOST_cold: "http://minio:minio123@127.0.0.1:9100"
ports:
- "9000:9000"
- "9001:9001"
- "9100:9100"
- "9101:9101"

prometheus:
image: prom/prometheus:latest
container_name: prometheus
command: ["--config.file=/etc/prometheus/prometheus.yml"]
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml:ro
ports:
- "9090:9090"
depends_on: [minio]

grafana:
image: grafana/grafana:latest
container_name: grafana
ports:
- "3000:3000"
environment:
GF_SECURITY_ADMIN_USER: admin
GF_SECURITY_ADMIN_PASSWORD: admin
depends_on: [prometheus]
244 changes: 244 additions & 0 deletions monitoring/grafana-dashboard.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,244 @@
{
"annotations": {
"list": [
{
"builtIn": 1,
"datasource": {
"type": "grafana",
"uid": "-- Grafana --"
},
"enable": true,
"hide": true,
"iconColor": "rgba(0, 211, 255, 1)",
"name": "Annotations & Alerts",
"type": "dashboard"
}
]
},
"description": "Dashboard showing MinIO bucket usage and PUT request latency\n",
"editable": true,
"fiscalYearStartMonth": 0,
"graphTooltip": 0,
"id": 1,
"links": [],
"panels": [
{
"datasource": {
"type": "prometheus",
"uid": "bew9cih96fx8gb"
},
"fieldConfig": {
"defaults": {
"color": {
"mode": "palette-classic"
},
"custom": {
"axisBorderShow": false,
"axisCenteredZero": false,
"axisColorMode": "text",
"axisLabel": "",
"axisPlacement": "auto",
"barAlignment": 0,
"barWidthFactor": 0.6,
"drawStyle": "line",
"fillOpacity": 0,
"gradientMode": "none",
"hideFrom": {
"legend": false,
"tooltip": false,
"viz": false
},
"insertNulls": false,
"lineInterpolation": "linear",
"lineWidth": 1,
"pointSize": 5,
"scaleDistribution": {
"type": "linear"
},
"showPoints": "auto",
"spanNulls": false,
"stacking": {
"group": "A",
"mode": "none"
},
"thresholdsStyle": {
"mode": "off"
}
},
"mappings": [],
"thresholds": {
"mode": "absolute",
"steps": [
{
"color": "green",
"value": 0
},
{
"color": "red",
"value": 80
}
]
}
},
"overrides": []
},
"gridPos": {
"h": 8,
"w": 12,
"x": 0,
"y": 0
},
"id": 2,
"options": {
"legend": {
"calcs": [],
"displayMode": "list",
"placement": "bottom",
"showLegend": true
},
"tooltip": {
"hideZeros": false,
"mode": "single",
"sort": "none"
}
},
"pluginVersion": "12.1.1",
"targets": [
{
"disableTextWrap": false,
"editorMode": "code",
"expr": "minio_s3_requests_ttfb_seconds_distribution{api=\"putobject\"}",
"fullMetaSearch": false,
"includeNullMetadata": false,
"legendFormat": "__auto",
"range": true,
"refId": "A",
"useBackend": false
}
],
"title": "PUT latency",
"type": "timeseries"
},
{
"datasource": {
"type": "prometheus",
"uid": "bew9cih96fx8gb"
},
"description": "minio_cluster_usage_total_bytes",
"fieldConfig": {
"defaults": {
"color": {
"mode": "palette-classic"
},
"custom": {
"axisBorderShow": false,
"axisCenteredZero": false,
"axisColorMode": "text",
"axisLabel": "",
"axisPlacement": "auto",
"barAlignment": 0,
"barWidthFactor": 0.6,
"drawStyle": "line",
"fillOpacity": 0,
"gradientMode": "none",
"hideFrom": {
"legend": false,
"tooltip": false,
"viz": false
},
"insertNulls": false,
"lineInterpolation": "linear",
"lineWidth": 1,
"pointSize": 5,
"scaleDistribution": {
"type": "linear"
},
"showPoints": "auto",
"spanNulls": false,
"stacking": {
"group": "A",
"mode": "none"
},
"thresholdsStyle": {
"mode": "off"
}
},
"mappings": [],
"thresholds": {
"mode": "absolute",
"steps": [
{
"color": "green",
"value": 0
},
{
"color": "red",
"value": 80
}
]
},
"unit": "bytes"
},
"overrides": []
},
"gridPos": {
"h": 8,
"w": 12,
"x": 0,
"y": 8
},
"id": 1,
"options": {
"legend": {
"calcs": [],
"displayMode": "list",
"placement": "bottom",
"showLegend": true
},
"tooltip": {
"hideZeros": false,
"mode": "single",
"sort": "none"
}
},
"pluginVersion": "12.1.1",
"targets": [
{
"datasource": {
"type": "prometheus",
"uid": "bew9cih96fx8gb"
},
"disableTextWrap": false,
"editorMode": "code",
"exemplar": false,
"expr": "minio_cluster_usage_total_bytes",
"fullMetaSearch": false,
"includeNullMetadata": true,
"instant": false,
"interval": "",
"legendFormat": "__auto",
"range": true,
"refId": "A",
"useBackend": false
}
],
"title": "Bucket size",
"type": "timeseries"
}
],
"preload": false,
"schemaVersion": 41,
"tags": [],
"templating": {
"list": []
},
"time": {
"from": "now-3h",
"to": "now"
},
"timepicker": {},
"timezone": "browser",
"title": "MinIO Monitoring",
"uid": "83c84814-bdf4-4a16-b3a0-b2cf9ae50de8",
"version": 3
}
Loading