Merge dev into main for v0.2.1
This commit is contained in:
commit
1dc5b51020
4 files changed
+39
-16
No files matched your search
@@ -1,17 +1,21 @@
|
|||||||
name: MindSift CI & Docker Release
|
name: MindSift CI & Docker Release
|
||||||
|
|
||||||
|
# Image tags:
|
||||||
|
# push to dev -> :dev
|
||||||
|
# push/merge main -> :latest
|
||||||
|
# git tag v1.2.0 -> :v1.2.0 and :stable
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
branches-ignore:
|
branches:
|
||||||
|
- dev
|
||||||
- main
|
- main
|
||||||
tags:
|
tags:
|
||||||
- '*'
|
- 'v*'
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
build-test-push:
|
build-test-push:
|
||||||
name: Build, Test in Container & Push
|
name: Build, Test in Container & Push
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
if: github.ref != 'refs/heads/main'
|
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout Code
|
- name: Checkout Code
|
||||||
uses: actions/checkout@v4
|
uses: actions/checkout@v4
|
||||||
@@ -33,9 +37,17 @@ jobs:
|
|||||||
# Ersetze evtl. Slashes in Branch-Namen (z.B. rc/1.1 -> rc-1.1) für valide Docker-Tags
|
# Ersetze evtl. Slashes in Branch-Namen (z.B. rc/1.1 -> rc-1.1) für valide Docker-Tags
|
||||||
DOCKER_TAG=$(echo "${REF_NAME}" | sed 's#/#-#g' | tr '[:upper:]' '[:lower:]')
|
DOCKER_TAG=$(echo "${REF_NAME}" | sed 's#/#-#g' | tr '[:upper:]' '[:lower:]')
|
||||||
|
|
||||||
|
# All tags of this run (space separated)
|
||||||
|
case "${GITHUB_REF:-}" in
|
||||||
|
refs/tags/*) TAGS="${DOCKER_TAG} stable" ;;
|
||||||
|
refs/heads/main) TAGS="latest" ;;
|
||||||
|
*) TAGS="${DOCKER_TAG}" ;;
|
||||||
|
esac
|
||||||
|
|
||||||
echo "registry=${REGISTRY_HOST}" >> "$GITHUB_OUTPUT"
|
echo "registry=${REGISTRY_HOST}" >> "$GITHUB_OUTPUT"
|
||||||
echo "image=${IMAGE_NAME}" >> "$GITHUB_OUTPUT"
|
echo "image=${IMAGE_NAME}" >> "$GITHUB_OUTPUT"
|
||||||
echo "tag=${DOCKER_TAG}" >> "$GITHUB_OUTPUT"
|
echo "tag=${TAGS%% *}" >> "$GITHUB_OUTPUT"
|
||||||
|
echo "tags=${TAGS}" >> "$GITHUB_OUTPUT"
|
||||||
echo "actor=${ACTOR_NAME}" >> "$GITHUB_OUTPUT"
|
echo "actor=${ACTOR_NAME}" >> "$GITHUB_OUTPUT"
|
||||||
# Releases (tags) show the tag as version in the app header
|
# Releases (tags) show the tag as version in the app header
|
||||||
APP_VERSION=""
|
APP_VERSION=""
|
||||||
@@ -43,7 +55,7 @@ jobs:
|
|||||||
refs/tags/*) APP_VERSION="${REF_NAME}" ;;
|
refs/tags/*) APP_VERSION="${REF_NAME}" ;;
|
||||||
esac
|
esac
|
||||||
echo "app_version=${APP_VERSION}" >> "$GITHUB_OUTPUT"
|
echo "app_version=${APP_VERSION}" >> "$GITHUB_OUTPUT"
|
||||||
echo "Target Docker image: ${IMAGE_NAME}:${DOCKER_TAG} (Registry: ${REGISTRY_HOST}, Actor: ${ACTOR_NAME})"
|
echo "Target Docker image: ${IMAGE_NAME} tags: ${TAGS} (Registry: ${REGISTRY_HOST}, Actor: ${ACTOR_NAME})"
|
||||||
|
|
||||||
- name: Login to Gitea Container Registry
|
- name: Login to Gitea Container Registry
|
||||||
uses: docker/login-action@v3
|
uses: docker/login-action@v3
|
||||||
@@ -54,8 +66,10 @@ jobs:
|
|||||||
|
|
||||||
- name: Build & Run All Checks in Container, then Push
|
- name: Build & Run All Checks in Container, then Push
|
||||||
run: |
|
run: |
|
||||||
FULL_IMAGE="${{ steps.prep.outputs.image }}:${{ steps.prep.outputs.tag }}"
|
IMAGE="${{ steps.prep.outputs.image }}"
|
||||||
echo "🚀 Building container & executing Frontend/Backend checks inside image: ${FULL_IMAGE}"
|
TAG_ARGS=""
|
||||||
DOCKER_BUILDKIT=1 docker build --progress=plain --build-arg APP_VERSION="${{ steps.prep.outputs.app_version }}" -t "${FULL_IMAGE}" .
|
for t in ${{ steps.prep.outputs.tags }}; do TAG_ARGS="${TAG_ARGS} -t ${IMAGE}:${t}"; done
|
||||||
echo "✅ All checks & tests passed inside container! Pushing ${FULL_IMAGE}..."
|
echo "🚀 Building container & executing Frontend/Backend checks inside image: ${IMAGE} (tags: ${{ steps.prep.outputs.tags }})"
|
||||||
docker push "${FULL_IMAGE}"
|
DOCKER_BUILDKIT=1 docker build --progress=plain --build-arg APP_VERSION="${{ steps.prep.outputs.app_version }}" ${TAG_ARGS} .
|
||||||
|
echo "✅ All checks & tests passed inside container! Pushing..."
|
||||||
|
for t in ${{ steps.prep.outputs.tags }}; do docker push "${IMAGE}:${t}"; done
|
||||||
@@ -91,6 +91,8 @@ Stage 2 golang:1.23 go vet, go test, go build → /app/mindsift (
|
|||||||
Stage 3 alpine:3.21 nur Binary, ca-certificates, tzdata
|
Stage 3 alpine:3.21 nur Binary, ca-certificates, tzdata
|
||||||
```
|
```
|
||||||
|
|
||||||
|
**Image-Tags (CI):** Push auf `dev` → `:dev`; Push/Merge auf `main` → `:latest`; Git-Tag `v*` (z. B. `v1.2.0`) → `:v1.2.0` und `:stable`. Andere Branches bauen nicht.
|
||||||
|
|
||||||
Die angezeigte Version (Kopf der App) setzt der Build-Parameter `APP_VERSION`: Die CI übergibt bei Git-Tags den Tag-Namen (`v0.2`), sonst zeigt die App die Version aus `frontend/package.json` mit `-dev` (`v0.2-dev`). Umgesetzt in `frontend/vite.config.ts` und `frontend/src/version.ts`.
|
Die angezeigte Version (Kopf der App) setzt der Build-Parameter `APP_VERSION`: Die CI übergibt bei Git-Tags den Tag-Namen (`v0.2`), sonst zeigt die App die Version aus `frontend/package.json` mit `-dev` (`v0.2-dev`). Umgesetzt in `frontend/vite.config.ts` und `frontend/src/version.ts`.
|
||||||
|
|
||||||
Die Tests laufen beim Image-Build (Frontend: `npm run test:run`, Backend: `go test -v ./...`); ein Fehler bricht den Build ab. Frontend-Tests liegen unter `frontend/src/**/__tests__/` (Vitest + jsdom + Testing Library, Setup in `frontend/src/test/setup.ts`).
|
Die Tests laufen beim Image-Build (Frontend: `npm run test:run`, Backend: `go test -v ./...`); ein Fehler bricht den Build ab. Frontend-Tests liegen unter `frontend/src/**/__tests__/` (Vitest + jsdom + Testing Library, Setup in `frontend/src/test/setup.ts`).
|
||||||
@@ -128,7 +128,7 @@ Minimal:
|
|||||||
```yaml
|
```yaml
|
||||||
services:
|
services:
|
||||||
mindsift:
|
mindsift:
|
||||||
image: git.dsit.me/sandrodach/mindsift:v0.2 # feste Version; :dev = neuester Entwicklungsstand
|
image: git.dsit.me/sandrodach/mindsift:stable # oder feste Version (:v0.2); :latest = main, :dev = Entwicklungsstand
|
||||||
restart: unless-stopped
|
restart: unless-stopped
|
||||||
ports: ["8080:8080"]
|
ports: ["8080:8080"]
|
||||||
volumes: ["./data:/data"]
|
volumes: ["./data:/data"]
|
||||||
@@ -161,7 +161,7 @@ Rufe `http://localhost:8080` auf. Beim ersten Start führt ein Assistent durch d
|
|||||||
* **Reverse-Proxy:** Am besten WebSocket-Upgrade und ungepufferte SSE-Streams durchreichen. Blockiert ein Proxy beides, funktioniert MindSift trotzdem über Long-Polling bzw. regelmäßige Abfragen, nur etwas träger. Beispiele für Nginx, Traefik, Caddy und Cloudflare: [Doku/reverse-proxy.md](Doku/reverse-proxy.md).
|
* **Reverse-Proxy:** Am besten WebSocket-Upgrade und ungepufferte SSE-Streams durchreichen. Blockiert ein Proxy beides, funktioniert MindSift trotzdem über Long-Polling bzw. regelmäßige Abfragen, nur etwas träger. Beispiele für Nginx, Traefik, Caddy und Cloudflare: [Doku/reverse-proxy.md](Doku/reverse-proxy.md).
|
||||||
* **Datensicherung:** Alle Daten liegen in `data/mindsift.db` (+ `-wal`/`-shm`). Sichere sie mit `sqlite3 mindsift.db ".backup 'backup.db'"` oder bei gestopptem Container. Zusätzlich gibt es einen JSON-Export pro Benutzer.
|
* **Datensicherung:** Alle Daten liegen in `data/mindsift.db` (+ `-wal`/`-shm`). Sichere sie mit `sqlite3 mindsift.db ".backup 'backup.db'"` oder bei gestopptem Container. Zusätzlich gibt es einen JSON-Export pro Benutzer.
|
||||||
* **Updates:** Neues Image ziehen und Container neu starten (`docker compose pull && docker compose up -d`). Das Schema wird beim Start automatisch angepasst. Die laufende Version steht im Kopf der App unter dem Namen.
|
* **Updates:** Neues Image ziehen und Container neu starten (`docker compose pull && docker compose up -d`). Das Schema wird beim Start automatisch angepasst. Die laufende Version steht im Kopf der App unter dem Namen.
|
||||||
* **Image-Tags:** Jeder Git-Tag erzeugt ein gleichnamiges Image (`:v0.2`), jeder Branch eines mit dem Branch-Namen (`:dev`).
|
* **Image-Tags:** `:dev` = Stand des Branches `dev`, `:latest` = Stand von `main`, `:stable` = zuletzt veröffentlichte Version. Ein Git-Tag wie `v1.2.0` erzeugt `:v1.2.0` und verschiebt `:stable` darauf.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
|||||||
@@ -816,13 +816,19 @@ export const OutlinerBlock: React.FC<OutlinerBlockProps> = ({
|
|||||||
{block.type === 'todo' && (
|
{block.type === 'todo' && (
|
||||||
<span className="inline-flex items-center align-middle ml-1.5 gap-1 shrink-0 pointer-events-auto z-10 relative select-none">
|
<span className="inline-flex items-center align-middle ml-1.5 gap-1 shrink-0 pointer-events-auto z-10 relative select-none">
|
||||||
{block.taskId && (
|
{block.taskId && (
|
||||||
<span
|
<button
|
||||||
className="badge-accent text-[9px] inline-flex items-center gap-0.5 px-1.5 py-0.2 rounded font-medium shrink-0"
|
type="button"
|
||||||
title="Mit erweiterter Aufgabe synchronisiert"
|
onMouseDown={(e) => e.stopPropagation()}
|
||||||
|
onClick={(e) => {
|
||||||
|
e.stopPropagation();
|
||||||
|
onOpenTask?.(block.taskId as string);
|
||||||
|
}}
|
||||||
|
className="badge-accent text-[9px] inline-flex items-center gap-0.5 px-1.5 py-0.2 rounded font-medium shrink-0 cursor-pointer hover:opacity-80"
|
||||||
|
title="Erweiterte Aufgabe öffnen"
|
||||||
>
|
>
|
||||||
<CheckSquare className="w-2.5 h-2.5" />
|
<CheckSquare className="w-2.5 h-2.5" />
|
||||||
<span>Erweitert</span>
|
<span>Erweitert</span>
|
||||||
</span>
|
</button>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{canEdit && (
|
{canEdit && (
|
||||||
@@ -861,6 +867,7 @@ export const OutlinerBlock: React.FC<OutlinerBlockProps> = ({
|
|||||||
type: 'todo',
|
type: 'todo',
|
||||||
};
|
};
|
||||||
onUpdateBlockRef.current(updatedBlock, true);
|
onUpdateBlockRef.current(updatedBlock, true);
|
||||||
|
onOpenTask?.(thought.id);
|
||||||
} catch (err: any) {
|
} catch (err: any) {
|
||||||
alert(err.message || 'Fehler beim Erstellen der erweiterten Aufgabe');
|
alert(err.message || 'Fehler beim Erstellen der erweiterten Aufgabe');
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in new issue
Block a user