瀏覽代碼

Algne import: ohmu serveri Docker Compose konfiguratsioonid

- main/ — põhiteenused (postgres, mariadb, qdrant, weaviate, jupyter, rocm-pytorch, rag-api, portainer)
- secondary/ — abiteenused (it-tools, vaultwarden, hop-web, hop-server)
- third/ — kolmandate osapoolte teenused per-teenus kaustades
- docker/ — eraldiseisvad skriptid
ardo 1 月之前
當前提交
6341be663b
共有 100 個文件被更改,包括 3972 次插入0 次删除
  1. 39 0
      .gitignore
  2. 129 0
      LOEMIND.md
  3. 15 0
      docker/pytorch.sh
  4. 59 0
      docker/pytorch2.sh
  5. 31 0
      main/.env.example
  6. 4 0
      main/Dockerfile/rag-api/.dockerignore
  7. 15 0
      main/Dockerfile/rag-api/Dockerfile
  8. 19 0
      main/Dockerfile/rag-api/LOEMIND.md
  9. 14 0
      main/Dockerfile/rag-api/requirements.txt
  10. 8 0
      main/LICENSE
  11. 153 0
      main/LOEMIND.md
  12. 3 0
      main/README.md
  13. 165 0
      main/README/PyTorch_ROCm_vs_JupyterLab.md
  14. 87 0
      main/README/README_RAG-API.md
  15. 48 0
      main/README/README_ollama.md
  16. 271 0
      main/README/README_searxng.md
  17. 7 0
      main/cleanup.sh
  18. 250 0
      main/docker-compose.yml
  19. 11 0
      main/init-db/01-create-openwebui-db.sql
  20. 29 0
      main/init-db/01-init-postgis.sql
  21. 28 0
      main/patches/patch_ollama_embeddings.py
  22. 11 0
      main/qdrant-config.yaml
  23. 9 0
      main/run.sh
  24. 55 0
      main/scripts/install-pgvector.sh
  25. 10 0
      secondary/.env.example
  26. 8 0
      secondary/LICENSE
  27. 74 0
      secondary/LOEMIND.md
  28. 3 0
      secondary/README.md
  29. 7 0
      secondary/cleanup.sh
  30. 101 0
      secondary/docker-compose.yml
  31. 10 0
      secondary/run.sh
  32. 65 0
      third/R/r-studio/r-studio/LOEMIND.md
  33. 66 0
      third/R/r-studio/r-studio/LOEMIND.txt
  34. 21 0
      third/R/r-studio/r-studio/cleanup.sh
  35. 41 0
      third/R/r-studio/r-studio/docker-compose.yml
  36. 45 0
      third/R/r-studio/r-studio/run.sh
  37. 13 0
      third/R/r-studio/r-studio/scripts/cron.sh
  38. 70 0
      third/R/shiny/paberkrohv/LOEMIND.md
  39. 39 0
      third/R/shiny/paberkrohv/LOEMIND.txt
  40. 21 0
      third/R/shiny/paberkrohv/cleanup.sh
  41. 41 0
      third/R/shiny/paberkrohv/docker-compose.yml
  42. 39 0
      third/R/shiny/paberkrohv/run.sh
  43. 82 0
      third/browserless/LOEMIND.md
  44. 66 0
      third/browserless/LOEMIND.txt
  45. 7 0
      third/browserless/cleanup.sh
  46. 87 0
      third/browserless/docker-compose.yml
  47. 6 0
      third/browserless/run.sh
  48. 23 0
      third/drupal/arilix/LOEMIND.txt
  49. 7 0
      third/drupal/arilix/cleanup.sh
  50. 19 0
      third/drupal/arilix/config/arilix.json
  51. 57 0
      third/drupal/arilix/docker-compose.yml
  52. 6 0
      third/drupal/arilix/run.sh
  53. 二進制
      third/drupal/arilix/xxx/bussikeskus.tar.gz
  54. 19 0
      third/drupal/bussikeskus/config/bussikeskus.json
  55. 50 0
      third/drupal/bussikeskus/docker-compose.yml
  56. 36 0
      third/drupal/bussikeskus/sync_from_arilix.sh
  57. 23 0
      third/drupal/merbond/LOEMIND.txt
  58. 7 0
      third/drupal/merbond/cleanup.sh
  59. 19 0
      third/drupal/merbond/config/merbond.json
  60. 56 0
      third/drupal/merbond/docker-compose.yml
  61. 6 0
      third/drupal/merbond/run.sh
  62. 59 0
      third/drupal/mustikas/LOEMIND.md
  63. 39 0
      third/drupal/mustikas/LOEMIND.txt
  64. 1 0
      third/drupal/mustikas/account.conf
  65. 2 0
      third/drupal/mustikas/ca/acme-v02.api.letsencrypt.org/ca.conf
  66. 7 0
      third/drupal/mustikas/cleanup.sh
  67. 19 0
      third/drupal/mustikas/config/mustikas.json
  68. 58 0
      third/drupal/mustikas/docker-compose.yml
  69. 12 0
      third/drupal/mustikas/http.header
  70. 27 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/ca.cer
  71. 58 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/fullchain.cer
  72. 31 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.cer
  73. 15 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.conf
  74. 17 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.csr
  75. 8 0
      third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.csr.conf
  76. 6 0
      third/drupal/mustikas/run.sh
  77. 25 0
      third/drupal/mustikas/sertifikaatide_genereerimine.sh
  78. 39 0
      third/drupal/mustikas/sync_from_hetzner.sh
  79. 59 0
      third/drupal/see1/LOEMIND.md
  80. 23 0
      third/drupal/see1/LOEMIND.txt
  81. 7 0
      third/drupal/see1/cleanup.sh
  82. 19 0
      third/drupal/see1/config/see1.json
  83. 63 0
      third/drupal/see1/docker-compose.yml
  84. 11 0
      third/drupal/see1/run.sh
  85. 23 0
      third/drupal/terminator/LOEMIND.txt
  86. 7 0
      third/drupal/terminator/cleanup.sh
  87. 19 0
      third/drupal/terminator/config/terminator.json
  88. 65 0
      third/drupal/terminator/docker-compose.yml
  89. 9 0
      third/drupal/terminator/run.sh
  90. 17 0
      third/drupal/terminator/scripts/composer_install.sh
  91. 102 0
      third/n8n/LOEMIND.md
  92. 13 0
      third/n8n/README.md
  93. 7 0
      third/n8n/backup_sqlite.sh
  94. 7 0
      third/n8n/cleanup.sh
  95. 16 0
      third/n8n/config/n8n.json
  96. 109 0
      third/n8n/docker-compose.yml
  97. 45 0
      third/n8n/n8n-custom-runner/Dockerfile
  98. 58 0
      third/n8n/n8n-custom-runner/n8n-task-runners.json
  99. 19 0
      third/n8n/run.sh
  100. 141 0
      third/server/anythingllm/LOEMIND.md

+ 39 - 0
.gitignore

@@ -0,0 +1,39 @@
+**/cache/
+**/__pycache__/
+**/data/
+**/archive/
+**/state/
+**/repo/
+**/models/
+**/node_modules/
+
+# Env
+**.env
+!.env.example
+
+# Editor
+*.swp
+*.swo
+*~
+.DS_Store
+Thumbs.db
+.idea/
+.vscode/
+
+# Docker
+**/pgdata/
+**/mysql/
+
+# OS
+lost+found/
+
+# Nested git repos (arengu kloonid — terved projektid, mitte compose konfiguratsioon)
+third/server/agenticSeek/
+third/server/mcp-filesystem/servers/
+third/server/odysseus/repo/
+
+# SSL võtmed ja sertifikaadid (tundlikud)
+**/*.key
+**/id_ed25519
+**/id_ed25519.pub
+**/account.json

+ 129 - 0
LOEMIND.md

@@ -0,0 +1,129 @@
+# Docker Compose — ülevaade
+
+Kõik arvuti `ohmu` Docker konteinerid on hallatud docker-compose kaudu.
+Kataloog: `/opt/docker-compose/`
+
+## Struktuur
+
+```
+/opt/docker-compose/
+├── LOEMIND.md              ← see fail
+├── main/                   # Peamised teenused (8 konteinerit)
+│   ├── docker-compose.yml
+│   ├── qdrant-config.yaml
+│   ├── LOEMIND.md
+│   ├── run.sh
+│   └── ...
+├── secondary/              # Abiteenused (1 konteiner)
+│   └── docker-compose.yml
+└── third/                  # Kolmandate osapoolte teenused (24 konteinerit)
+    ├── browserless/        # Selenium + browserless (4)
+    ├── drupal/             # Drupal saidid (mustikas, see1, merbond, arilix, terminator)
+    ├── n8n/                # N8N töövooautomaatika (3)
+    ├── R/                  # RStudio + Shiny (2)
+    └── server/             # Serveriteenused (13)
+        ├── agenticSeek/
+        ├── anythingllm/
+        ├── flaresolverr/
+        ├── mcp-filesystem/
+        ├── ollama/         # ⚠ Ei kasutata — asendatud native installiga
+        ├── openwebui/
+        ├── redis/
+        ├── searngx/
+        └── ...
+```
+
+## Kõik teenused (33 konteinerit)
+
+| Projekt | Konteiner | Port | Compose fail |
+|---------|-----------|------|-------------|
+| **main** | mariadb | 3306 | `main/docker-compose.yml` |
+| | postgres_postgis | 5432 | |
+| | qdrant | 6333-6334 | |
+| | rag_api | 8072 | |
+| | jupyter | 8887 | |
+| | portainer | 9000, 9443 | |
+| | rocm_pytorch | 8889, 6006 | |
+| | weaviate | 8080, 50051 | |
+| **n8n** | n8n | 5678 | `third/n8n/docker-compose.yml` |
+| | n8n-runners | 5680 | |
+| | playwright | 3003 | |
+| | ts-n8n | tailscale | |
+| **openwebui** | open-webui | 3010 | `third/server/openwebui/docker-compose.yml` |
+| | mcp-terminal | 3110 | |
+| | tika | 9998 | |
+| **browserless** | selenium-hub | 4442-4444 | `third/browserless/docker-compose.yml` |
+| | selenium-chrome | 7900 | |
+| | selenium-firefox | 7901 | |
+| | browserless | 3001 | |
+| **mcp-filesystem** | mcp-filesystem | - | `third/server/mcp-filesystem/docker-compose.yml` |
+| | mcp-filesystem-sse | 3100 | |
+| **mustikas** | drupal_mustikas | - | `third/drupal/mustikas/docker-compose.yml` |
+| | ts-mustikas | tailscale | |
+| **see1** | drupal_see1 | - | `third/drupal/see1/docker-compose.yml` |
+| | ts-see1 | tailscale | |
+| **redis** | redis | 6379 | `third/server/redis/docker-compose.yml` |
+| **searngx** | searxng | 8888 | `third/server/searngx/docker-compose.yml` |
+| **flaresolverr** | flaresolverr | 8191 | `third/server/flaresolverr/docker-compose.yml` |
+| **secondary** | it-tools | 9101 | `secondary/docker-compose.yml` |
+| **anythingllm** | anythingllm | 3002 | `third/server/anythingllm/docker-compose.yml` |
+| **paberkrohv** | shiny-paberkrohv | 8013 | `third/R/shiny/paberkrohv/docker-compose.yml` |
+| **r-studio** | shiny-r-studio | 8012 | `third/R/r-studio/r-studio/docker-compose.yml` |
+
+## Mitteaktiivsed compose failid
+
+Need compose failid on olemas aga teenused pole käivitatud:
+
+| Compose fail | Põhjus |
+|-------------|--------|
+| `third/server/ollama/` | Asendatud native systemd installiga (port 11434) |
+| `third/server/agenticSeek/` | Pole käivitatud |
+| `third/drupal/merbond/` | Pole käivitatud |
+| `third/drupal/arilix/` | Pole käivitatud |
+| `third/drupal/terminator/` | Pole käivitatud |
+| `third/stirling-pdf/` | Pole käivitatud |
+| `secondary/` vaultwarden | Pole käivitatud |
+
+## Kõigi teenuste taaskäivitamine
+
+```bash
+# Kõik korraga
+cd /opt/docker-compose/main && docker-compose up -d
+cd /opt/docker-compose/secondary && docker-compose up -d
+for d in /opt/docker-compose/third/*/ /opt/docker-compose/third/*/*/; do
+  [ -f "$d/docker-compose.yml" ] && (cd "$d" && docker-compose up -d)
+done
+```
+
+## Kontroll — kas kõik on compose hallatud?
+
+```bash
+docker ps --format '{{.Names}}' | while read name; do
+  project=$(docker inspect "$name"     --format '{{json .Config.Labels}}'     | python3 -c 'import json,sys; d=json.load(sys.stdin); print(d.get("com.docker.compose.project","NONE"))')
+  echo "$name -> $project"
+done
+# Kõik peavad näitama compose projekti nime, mitte NONE
+```
+
+## Võrguinfo
+
+Kõik konteinerid kasutavad võrku `main_ai_network` (compose'is `ai_network`).
+Tailscale konteinerid (`ts-*`) pakuvad ligipääsu läbi Tailscale VPN-i.
+
+## Väljaspool compose'i
+
+| Teenus | Asukoht | Põhjus |
+|--------|---------|--------|
+| **Ollama** | Native systemd (`ollama.service`), port 11434 | GPU tugi ROCm 7.2.2 kaudu |
+| **llama.cpp** | Native protsess (`llama-server`), port 8070 | Suure mudeli serveerimine (116B params) |
+
+## Ajalugu
+
+| Kuupäev | Muudatus |
+|---------|----------|
+| 2025-07-05 | Kõik 33 konteinerit viidud docker-compose haldusesse (12 compose + 19 docker run + 1 orphan → 33 compose) |
+| 2025-07-05 | Qdrant parandatud: healthcheck, config mount, compose haldus |
+| 2025-07-05 | OpenWebUI: ulimits 1024→65536, embedding GPU-le, compose haldus |
+| 2025-07-05 | AnythingLLM: compose haldus, llama.cpp Generic OpenAI seadistus |
+| 2025-07-05 | Ollama viidud Dockerist native systemd peale (ROCm GPU) |
+| 2025-07-05 | mcp-filesystem-sse lisatud compose faili |

+ 15 - 0
docker/pytorch.sh

@@ -0,0 +1,15 @@
+# Tõmba scottt Docker image
+docker pull scottt/therock:pytorch-vision-dev-f41
+
+# Käivita GPU ligipääsuga
+docker run -it --rm \
+    --device=/dev/kfd \
+    --device=/dev/dri \
+    --privileged \
+    -v ~/rag-demo/pdf-pipeline/data:/data \
+    scottt/therock:pytorch-vision-dev-f41 \
+    bash
+
+# Dockeroi sees:
+pip install marker-pdf
+marker /data/xxx /data/markdown_output --workers 8

+ 59 - 0
docker/pytorch2.sh

@@ -0,0 +1,59 @@
+#!/bin/bash
+
+DOCKER_NAME=pytorch_rocm
+docker stop ${DOCKER_NAME} && docker rm ${DOCKER_NAME}
+
+# --rm -it
+docker run -d -ti --name=${DOCKER_NAME} \
+  --device=/dev/kfd \
+  --device=/dev/dri \
+  --security-opt seccomp=unconfined \
+  --shm-size=8G \
+  -v $HOME:/workspace \
+  rocm/pytorch:rocm7.2_ubuntu24.04_py3.12_pytorch_release_2.9.1
+
+sleep 5
+# konteineri sees 
+docker exec -ti -u 0 ${DOCKER_NAME} bash -c "
+echo 'TORCH_ROCM_AOTRITON_ENABLE_EXPERIMENTAL=1' >> /root/.bashrc;
+source /root/.bashrc;
+pip install --upgrade pip;
+pip install --upgrade pip;
+pip install marker-pdf;
+"
+# Kontrolli GPU kasutamist konteineri sees:
+docker exec -ti -u 0 ${DOCKER_NAME} python3 -c "import torch; print(torch.cuda.is_available())"
+# Peaks väljastama `True`
+docker exec -ti -u 0 ${DOCKER_NAME} python3 -c "import torch; print(torch.cuda.get_device_name(0))"
+
+# GPU kontrollimine (kui käivitada midagi docker'i sees, siis on näha)
+amd-smi
+
+# Dockeri parameetrite selgitus
+#   - `--rm`: Kustutab konteineri pärast väljumist.
+#   - `-it`: Interaktiivne terminal.
+#   - `--device=/dev/kfd --device=/dev/dri`: Annab juurdepääsu AMD GPU seadmetele ROCm-i jaoks.
+#   - `--security-opt seccomp=unconfined`: Vajalik mõnede ROCm funktsioonide jaoks (nt HSA).
+#   - `--shm-size=8G`: Suurendab jagatud mälu (kasulik suurte mudelite jaoks, nt AI-tööd).
+#   - `-v $HOME:/workspace`: Ühendab sinu kodukataloogi konteineri sisse, et saaksid faile jagada.
+
+docker exec -ti -u 0 ${DOCKER_NAME} bash -c "
+input_dir=/workspace/rag-demo/pdf-pipeline/data/raw_pdfs \
+output_dir=/workspace/rag-demo/pdf-pipeline/data/markdown_output \
+cd \"$input_dir\" \
+for file in *.pdf; do \
+    base=\"${file%.pdf}\" \
+    outdir=\"$output_dir\"/\"$base\" \
+    if [ -d "$outdir" ]; then \
+        echo \"Jätan vahele (kaust olemas): $file\" \
+        continue \
+    fi \
+        echo \"Töötlen pdf faili: $file\" \
+    marker_single \"$file\" --output_dir \"$output_dir\" \
+done
+"
+
+
+
+     
+               

+ 31 - 0
main/.env.example

@@ -0,0 +1,31 @@
+# main stack — keskkonnamuutujad
+# Kopeeri .env.example -> .env ja täida päris väärtused
+
+# PostgreSQL
+POSTGRES_USER=ai_user
+POSTGRES_PASSWORD=change_me
+POSTGRES_DB=research_db
+
+# MariaDB
+MYSQL_ROOT_PASSWORD=change_me
+MYSQL_DATABASE=research_mariadb
+MYSQL_USER=ai_mariadb_user
+MYSQL_PASSWORD=change_me
+
+# Jupyter
+JUPYTER_TOKEN=change_me
+
+# ROCm PyTorch
+PYTORCH_TOKEN=change_me
+
+# RAG API
+LLAMA_CPP_URL=http://100.87.1.24:8070/completion
+DB_HOST=postgres
+DB_PORT=5432
+DB_NAME=pdf_research
+DB_USER=osm
+DB_PASSWORD=change_me
+OLLAMA_URL=http://100.87.1.24:11434
+
+# Ajavöönd
+TZ=Europe/Tallinn

+ 4 - 0
main/Dockerfile/rag-api/.dockerignore

@@ -0,0 +1,4 @@
+# välista PyTorch workspace ja prügikast
+main/pytorch-workspace
+**/.Trash-0
+**/.Trash-*

+ 15 - 0
main/Dockerfile/rag-api/Dockerfile

@@ -0,0 +1,15 @@
+FROM python:3.12-slim
+
+# Build-tools
+RUN apt-get update && apt-get install -y \
+    build-essential g++ gcc \
+    && rm -rf /var/lib/apt/lists/*
+
+WORKDIR /app
+
+RUN pip install --upgrade pip
+COPY requirements.txt .
+RUN pip install --no-cache-dir -r requirements.txt
+
+# MUUDA SEDA RIDA:
+CMD ["python", "-m", "uvicorn", "src.rag_api:app", "--host", "0.0.0.0", "--port", "8000"]

+ 19 - 0
main/Dockerfile/rag-api/LOEMIND.md

@@ -0,0 +1,19 @@
+
+cd /opt/docker-compose/rag-api
+
+cat > .dockerignore << 'EOF'
+# välista PyTorch workspace ja prügikast
+main/pytorch-workspace
+**/.Trash-0
+**/.Trash-*
+EOF
+
+
+docker build -t rag-api .
+docker run -p 8072:8000 rag-api
+
+docker run --rm -p 8072:8000 \
+  -v ~/rag-demo/pdf-pipeline/src:/app/src \
+  rag-api \
+  uvicorn src.rag_api:app --host 0.0.0.0 --port 8000
+

+ 14 - 0
main/Dockerfile/rag-api/requirements.txt

@@ -0,0 +1,14 @@
+fastapi==0.109.0
+uvicorn==0.27.0
+pydantic==2.12.0
+python-multipart==0.0.6
+langchain==0.1.7
+ollama==0.6.0
+openai==1.3.9
+weaviate-client==4.19.0
+pypdf==4.0.1
+python-docx==1.0.1
+requests==2.31.0
+python-dotenv==1.0.0
+psycopg2-binary
+sentence_transformers

+ 8 - 0
main/LICENSE

@@ -0,0 +1,8 @@
+MIT License
+Copyright (c) <year> <copyright holders>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

+ 153 - 0
main/LOEMIND.md

@@ -0,0 +1,153 @@
+# Peamised teenused (main) – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/main/`
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| portainer | portainer/portainer-ce | 9000, 9443 | Docker halduse veebiliides |
+| postgres_postgis | kartoza/postgis:16 | 5432 | PostgreSQL + GIS |
+| mariadb | mariadb:11 | 3306 | MySQL-ühilduv andmebaas |
+| weaviate | semitechnologies/weaviate | 8080, 50051 | Vektorandmebaas |
+| qdrant | qdrant/qdrant | 6333, 6334 | Vektorandmebaaas |
+| jupyter | jupyter/datascience-notebook | 8887 | Python andmeteaduse töölaud |
+| rocm_pytorch | rocm/pytorch | 8889, 6006 | PyTorch AMD GPU-ga |
+| rag_api | custom (Dockerfile) | 8072 | RAG API |
+
+## Docker käsud
+
+```bash
+# Käivita kõik
+docker-compose -f /opt/docker-compose/main/docker-compose.yml up -d
+
+# Peata kõik
+docker-compose -f /opt/docker-compose/main/docker-compose.yml down
+
+# Taaskäivita üks teenus
+docker-compose -f /opt/docker-compose/main/docker-compose.yml restart portainer
+
+# Logid (kõik)
+docker-compose -f /opt/docker-compose/main/docker-compose.yml logs -f
+
+# Logid (üks teenus)
+docker-compose -f /opt/docker-compose/main/docker-compose.yml logs -f jupyter
+```
+
+## Üksikud konteinerid
+
+```bash
+# Portainer
+docker logs portainer
+docker restart portainer
+
+# PostgreSQL
+docker logs postgres_postgis
+docker exec -it postgres_postgis psql -U ai_user -d research_db
+
+# MariaDB
+docker logs mariadb
+docker exec -it mariadb mariadb -u ai_mariadb_user -p
+
+# Jupyter
+docker logs jupyter
+# Ava brauseris: http://100.87.1.24:8887 (token: ai_server_2026)
+
+# ROCm PyTorch
+docker logs rocm_pytorch
+# Ava brauseris: http://100.87.1.24:8889 (token: ai_pytorch_2026)
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| Portainer | http://100.87.1.24:9000 |
+| Jupyter | http://100.87.1.24:8887 (token: ai_server_2026) |
+| ROCm PyTorch | http://100.87.1.24:8889 (token: ai_pytorch_2026) |
+| Weaviate | http://100.87.1.24:8080 |
+| Qdrant | http://100.87.1.24:6333 |
+| RAG API | http://100.87.1.24:8072 |
+
+## Andmebaaside paroolid
+
+| Teenus | Kasutaja | Parool |
+|--------|----------|--------|
+| PostgreSQL | ai_user | ai_secure_pass_2026 |
+| MariaDB | ai_mariadb_user | ai_mariadb_pass_2026 |
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/data/docker/jupyter/notebooks` | Jupyteri märkmikud |
+| `/data/docker/jupyter/data` | Jupyteri andmed |
+| `/data/docker/jupyter/pytorch-workspace` | PyTorch tööruum |
+| `/backups/docker/portainer` | Varukoopiad |
+| `/backups/docker/postgres` | Varukoopiad |
+| `/backups/docker/mariadb` | Varukoopiad |
+
+## Võrguinfo
+
+- Kõik konteinerid on `ai_network` peal
+- `rag-api` sõltub weaviate'ist ja postgres'ist
+
+
+## Qdrant seadistus
+
+### Healthcheck
+Qdrant pildil pole curl/wget. Healthcheck kasutab bash TCP kontrolli:
+```yaml
+healthcheck:
+  test: ["CMD", "bash", "-c", "</dev/tcp/localhost/6333"]
+  interval: 30s
+  timeout: 10s
+  retries: 3
+  start_period: 10s
+```
+
+### Config fail
+`/opt/docker-compose/main/qdrant-config.yaml` on monteeritud konteinerisse:
+```yaml
+volumes:
+  - qdrant_data:/qdrant/storage
+  - ./qdrant-config.yaml:/qdrant/config/production.yaml:ro
+```
+
+Config sisaldab:
+- `hnsw_ef_construct: 100` — HNSW indeksi kvaliteet
+- `hnsw_m: 16` — graafi ühenduvus
+- `on_disk: false` — vektorid RAM-is (kiirem)
+- `max_request_size_mb: 256` — suurte päringute tugi
+
+### Qdrant API test
+```bash
+# Tervisekontroll
+curl http://localhost:6333/health
+
+# Kollektsioonide loend
+curl http://localhost:6333/collections | jq
+
+# Kollektsiooni info
+curl http://localhost:6333/collections/open-webui_files | jq
+```
+
+### Andmete varundamine
+Andmed asuvad Docker volume's `qdrant_data`:
+```bash
+# Varunda Qdranti andmed
+docker run --rm -v qdrant_data:/data -v /backups/docker/qdrant:/backup \
+  alpine tar czf /backup/qdrant-backup-$(date +%Y%m%d).tar.gz -C /data .
+
+# Taasta
+docker run --rm -v qdrant_data:/data -v /backups/docker/qdrant:/backup \
+  alpine tar xzf /backup/qdrant-backup-YYYYMMDD.tar.gz -C /data
+```
+
+## Ajalugu
+
+| Kuupäev | Muudatus |
+|---------|----------|
+| 2025-07-05 | Qdrant viidud otse `docker run` pealt compose haldusesse |
+| 2025-07-05 | Qdrant healthcheck parandatud — `true` -> bash TCP kontroll |
+| 2025-07-05 | Qdrant config fail monteeritud (`qdrant-config.yaml`) |

+ 3 - 0
main/README.md

@@ -0,0 +1,3 @@
+# main
+
+Docker-compose failid

+ 165 - 0
main/README/PyTorch_ROCm_vs_JupyterLab.md

@@ -0,0 +1,165 @@
+# Erinevused PyTorch (ROCm) ja JupyterLab konteinerite vahel
+
+Suurepärane küsimus! Vaatame, mida kumbki pakub:
+
+## 🔴 **ROCm PyTorch konteiner** (`rocm_pytorch`, port 8889)
+
+### ✅ **Eelised:**
+
+- **GPU tugi AMD ROCm-iga** - kasutab sinu AMD Ryzen AI Max+ 395 GPU-d
+- **PyTorch eelinstallitud** - ROCm-iga kompileeritud, optimeeritud AMD GPU-le
+- **ML/DL raamistik** - transformers, BERT, GPT, neural networks
+- **Kiirus** - GPU kiirendus deep learning mudelitele
+- **96GB RAM juurdepääs** - kogu süsteemi RAM on kasutatav GPU tööks
+
+
+### ⚠️ **Puudused:**
+
+- **Suurem image** (~12GB) - võtab rohkem ruumi
+- **Keerulisem setup** - vajab `/dev/kfd`, `/dev/dri` device'e
+- **AMD-spetsiifiline** - ROCm töötab ainult AMD GPU-del
+- **Eksperimentaalne** - mõned funktsioonid (Flash Attention) on veel betas
+
+
+### 🎯 **Kasuta, kui:**
+
+- Teed **deep learning** (neural networks, transformers, LLM-id)
+- Vajad **GPU kiirendust** (suur andmehulk, suured mudelid)
+- Töötad **embeddings/vektorite** genereerimisega
+- Treenid **mudeleid** (fine-tuning, transfer learning)
+- Teadusartiklite **NLP analüüs** (BERT, SciBERT, BioBERT)
+
+***
+
+## 🔵 **JupyterLab konteiner** (`jupyter`, port 8888)
+
+### ✅ **Eelised:**
+
+- **Kerge** (~2GB image) - väiksem, kiirem käivitamine
+- **Laialdane toetus** - pandas, numpy, scipy, matplotlib, scikit-learn
+- **Andmeanalüüs** - statistika, visualiseerimine, exploratory data analysis
+- **Lihtne** - ei vaja GPU seadistust
+- **Stabiilne** - küps ökosüsteem
+
+
+### ⚠️ **Puudused:**
+
+- **Ei toeta GPU-d** - töötab ainult CPU-l
+- **Aeglasem deep learning** - ilma GPU-ta 10-100x aeglasem
+- **Ei ole PyTorch** - pead installeerima (aga CPU versioon)
+- **Piiratud ML** - scikit-learn on olemas, aga deep learning puudub
+
+
+### 🎯 **Kasuta, kui:**
+
+- Teed **andmeanalüüsi** (pandas, numpy, statistika)
+- **Visualiseerimine** (matplotlib, seaborn, plotly)
+- **Klassikaline ML** (scikit-learn: regression, clustering, classification)
+- **Kerge töö** - tabeliandmed, CSV, SQL päringud
+- **Ei vaja GPU-d** - väikesed andmehulgad
+
+***
+
+## 📊 Võrdlustabel
+
+| Kriteerium | ROCm PyTorch (port 8889) | JupyterLab (port 8888) |
+| :-- | :-- | :-- |
+| **GPU tugi** | ✅ AMD ROCm | ❌ Ainult CPU |
+| **PyTorch** | ✅ Eelinstallitud | ❌ Puudub |
+| **Deep Learning** | ✅ Neural networks | ❌ Ainult scikit-learn |
+| **Transformers** | ✅ BERT, GPT, LLM-id | ❌ Puudub |
+| **Pandas/NumPy** | ✅ Installitav | ✅ Eelinstallitud |
+| **Kiirus (DL)** | 🚀 GPU kiirendus | 🐌 CPU (10-100x aeglasem) |
+| **Image suurus** | ~12GB | ~2GB |
+| **Kasutusvaldkond** | ML/DL, NLP, Computer Vision | Andmeanalüüs, statistika |
+| **Stabiilsus** | ⚠️ Eksperimentaalne | ✅ Väga stabiilne |
+
+
+***
+
+## 🎯 Praktiline soovitus sinu projektile:
+
+### **Kasuta ROCm PyTorch (port 8889), kui:**
+
+```python
+# Teadusartiklite embeddingi-d
+from transformers import AutoModel
+model = AutoModel.from_pretrained("allenai/scibert_scivocab_uncased").to("cuda")
+
+# Neural network treenimine
+import torch.nn as nn
+model = MyNeuralNetwork().to("cuda")
+
+# Suur andmehulk
+for batch in large_dataset:
+    embeddings = model(batch.to("cuda"))
+```
+
+
+### **Kasuta JupyterLab (port 8888), kui:**
+
+```python
+# Andmeanalüüs
+import pandas as pd
+df = pd.read_csv('articles.csv')
+df.groupby('year').size().plot()
+
+# Statistika
+from scipy import stats
+stats.ttest_ind(group1, group2)
+
+# Klassikaline ML
+from sklearn.ensemble import RandomForestClassifier
+clf = RandomForestClassifier()
+clf.fit(X_train, y_train)
+```
+
+
+***
+
+## 💡 **Sinu projektis (teadusartiklite analüüs):**
+
+### **Ideaalne töövoog:**
+
+1. **ROCm PyTorch** → Genereeri embeddingi-d GPU-ga (kiire!)
+
+```python
+# port 8889
+embeddings = bert_model(articles).to("cuda")
+save_to_postgres(embeddings)
+```
+
+2. **JupyterLab** → Analüüsi tulemusi (pandas, plotly)
+
+```python
+# port 8888
+df = pd.read_sql("SELECT * FROM articles", conn)
+df['year'].value_counts().plot(kind='bar')
+```
+
+
+***
+
+## Kokkuvõte:
+
+| Stsenaarium | Konteiner |
+| :-- | :-- |
+| 🧠 **Deep learning, transformers, embeddingi-d** | ROCm PyTorch ✅ |
+| 📊 **Andmeanalüüs, visualiseerimine, statistika** | JupyterLab ✅ |
+| 🚀 **Suur andmehulk, mudelite treenimine** | ROCm PyTorch ✅ |
+| 📈 **SQL päringud, tabelid, graafikud** | JupyterLab ✅ |
+
+**Sinu projektis saad kasutada mõlemat paralleelselt:**
+
+- **ROCm PyTorch** → GPU-intensiivne töö (embeddingi-d)
+- **JupyterLab** → Kerge analüüs ja visualiseerimine
+
+**Kas on veel küsimusi Docker setup'i kohta?** 🚀
+<span style="display:none">[^1][^2]</span>
+
+<div align="center">⁂</div>
+
+[^1]: image.jpg
+
+[^2]: image.jpg
+

+ 87 - 0
main/README/README_RAG-API.md

@@ -0,0 +1,87 @@
+
+```bash
+curl -X POST "http://100.87.1.24:8072/search" \
+  -H "Content-Type: application/json" \
+  -d '{"query": "transport planning", "limit": 3}'
+```
+
+🎉🎉🎉 **SUUREPÄRANE!** Palju õnne!
+
+Näen, et RAG API **genereeris täielikult eesti keelses vastuse** – artikelite viidete, praktiliste rakenduste ja teaduslike järelduste abil!
+
+## ✅ Mis nüüd toimib
+
+- ✅ **Weaviate** – artikleid otsitakse ja leitakse
+- ✅ **Embeddings** – Weaviate teeb vector search'i
+- ✅ **PostgreSQL + pgvector** – pole kasutatud, aga baas on olemas
+- ✅ **llama.cpp LLM** – genereerib kvaliteetset eesti keelset teksti
+- ✅ **RAG pipeline** – konteksti ehitamine + LLM response generation
+- ✅ **Docker Compose** – kõik teenused käivad isoleeritud keskkonnaga
+
+***
+
+## 🚀 Järgmised sammud (soovitused)
+
+### 1. **Optimiseerimine**
+
+```bash
+# Kontrolli Docker ressursside kasutamist
+docker-compose stats
+```
+
+
+### 2. **Logging ja Monitoring**
+
+```bash
+# Pidevalt jälgi logisid
+docker-compose logs -f rag-api --tail 50
+
+# Või salvestada failesse
+docker-compose logs rag-api > /tmp/rag-api.log
+```
+
+
+### 3. **API dokumentatsioon**
+
+```bash
+# OpenAPI spec on olemas
+curl http://localhost:8072/openapi.json > /tmp/rag-api-openapi.json
+```
+
+
+### 4. **Backup strateegia**
+
+```bash
+# Weaviate andmete backup
+docker-compose exec weaviate tar czf - /var/lib/weaviate > /backup/weaviate-$(date +%Y%m%d).tar.gz
+
+# PostgreSQL dump
+docker-compose exec postgres pg_dump -U osm pdf_research > /backup/db-$(date +%Y%m%d).sql
+```
+
+
+### 5. **Health Check'ide parandamine**
+
+```bash
+# Kontrollida kõigi teenuste tervist
+curl http://localhost:8072/health
+curl http://localhost:8080/v1/.well-known/ready
+curl http://localhost:5432/  # PostgreSQL
+```
+
+
+***
+
+## 📋 Dokumentatsioon kokkuvõttes
+
+**Teie RAG API stack:**
+
+- 🔵 **Weaviate** (Vector DB): http://localhost:8080
+- 🟡 **llama.cpp** (LLM): http://localhost:8070
+- 🟢 **RAG API** (FastAPI): http://localhost:8072/docs
+- 🔴 **PostgreSQL** (pgvector): localhost:5432
+- 🟣 **Ollama**: http://localhost:11434 (olemas, aga ei kasuta)
+
+
+
+

+ 48 - 0
main/README/README_ollama.md

@@ -0,0 +1,48 @@
+# Ollama
+## Kuidas lisada mudeleid ollama jaoks.
+
+Osad mudelid, mis töötavad sul palja llama.cpp + ROCm/Vulkaniga võivad Ollama + ROCm + iGPU (gfx1151) peal ROCm‑backendiga „ROCm0 buffer“ vea anda, sest Ollama kasutab teisi mäluheuristikaid ja piiranguid kui sinu käsitsi kompileeritud llama.cpp.
+
+### Kuidas kasutada suuremaid mudeleid?
+Lae alla suurem mudel
+Kuida kombineerida GGUF-i URL-i:
+1. Otsi https://huggingface.co pealt sobiv mudel
+2. Otsi valik "Use this model" -> llama-cpp-python
+3. Võta sealt:
+  3.1 repo_id="BSC-LT/ALIA-40b-instruct-2512-GGUF"
+  3.2 filename="ALIA-40b-instruct-2512-Q8_0.gguf"
+4. Ühenda kõik see info nagu allpool koodis
+
+```bash
+mkdir -p /models/alia-40b
+cd /models/alia-40b
+
+wget https://huggingface.co/BSC-LT/ALIA-40b-instruct-2512-GGUF/resolve/main/ALIA-40b-instruct-2512-Q8_0.gguf \
+  -O ALIA-40b-instruct-2512-Q8_0.gguf
+
+# Loo Modelfile
+cat > Modelfile << 'EOF'
+FROM ./ALIA-40b-instruct-2512-Q8_0.gguf
+
+PARAMETER temperature 0.7
+PARAMETER top_p 0.9
+PARAMETER top_k 40
+PARAMETER repeat_penalty 1.1
+PARAMETER num_gpu 18
+
+TEMPLATE """You are a helpful multilingual assistant. Always answer in Estonian unless the user explicitly asks for another language.
+
+{{ .Prompt }}"""
+EOF
+# Docker'i konteineri
+docker exec -it ollama bash
+
+cd /models/alia-40b
+ollama create ALIA-40b-instruct-est-2512-Q8_0 -f /models/Modelfiles/Modelfile
+
+ollama list
+ollama run ALIA-40b-instruct-est-2512-Q8_0
+
+
+```
+

+ 271 - 0
main/README/README_searxng.md

@@ -0,0 +1,271 @@
+# SearXNG ja Open WebUI integratsioon 
+
+```markdown
+# SearXNG + Open WebUI integratsioon (ohmu server)
+
+See juhend kirjeldab, kuidas SearXNG töötab koos Open WebUI‑ga ja milliseid seadeid me muutsime.
+
+## 1. Asukoht ja käivitamine
+
+Projektikataloog:
+
+```bash
+cd /opt/docker-compose/main
+```
+
+Põhikäsklused:
+
+```bash
+# Kõik teenused taustal
+docker-compose up -d
+
+# Ainult SearXNG
+docker-compose up -d searxng
+
+# Ainult Open WebUI
+docker-compose up -d open-webui
+
+# Logid
+docker logs -f searxng
+docker logs -f open-webui
+```
+
+
+---
+
+## 2. SearXNG seadistus
+
+### 2.1 Docker Compose teenus
+
+Fail: `docker-compose.yml`
+
+```yaml
+searxng:
+  image: searxng/searxng:latest
+  container_name: searxng
+  restart: always
+  ports:
+    - "8888:8080"
+  volumes:
+    - ./searxng:/etc/searxng:rw
+  environment:
+    - SEARXNG_BASE_URL=http://100.87.1.24:8888/
+    - SEARXNG_SECRET=searxng_secret_key_change_me_2026_random_string
+    - TZ=Europe/Tallinn
+  networks:
+    - ai_network
+  healthcheck:
+    test: ["CMD", "wget", "--spider", "-q", "http://localhost:8080/healthz"]
+    interval: 30s
+    timeout: 10s
+    retries: 3
+    start_period: 30s
+```
+
+
+### 2.2 `settings.yml` olulisemad read
+
+Fail: `./searxng/settings.yml` (mount’itud konteinerisse `/etc/searxng/settings.yml`)
+
+```yaml
+server:
+  port: 8080          # sisemine port konteineris
+  bind_address: "0.0.0.0"
+  base_url: false
+  limiter: false      # rate limiting / botdetection välja
+  public_instance: false
+  method: "GET"
+
+formats:
+  - html
+  - json              # vajalik, et Open WebUI saaks JSON-tulemusi
+```
+
+DuckDuckGo CAPTCHAd vältimiseks on DDG mootorid soovi korral keelatud:
+
+```yaml
+- name: duckduckgo
+  engine: duckduckgo
+  shortcut: ddg
+  disabled: true
+```
+
+(jne kõik ddg‑* mootorid `disabled: true`).
+
+### 2.3 Limiter konfiguratsioon (valikuline)
+
+Fail: `./searxng/limiter.toml`
+
+```toml
+[botdetection.ip_limit]
+filter_link_local = false
+link_token = false
+
+[botdetection.ip_lists]
+pass_ip = [
+  "172.16.0.0/12",
+  "10.0.0.0/8",
+  "192.168.0.0/16"
+]
+```
+
+NB! Kuigi logides on hoiatus `X-Forwarded-For nor X-Real-IP header is set!`, tänu `limiter: false` ei blokita päringuid – seda hoiatust võib ignoreerida.
+
+---
+
+## 3. Open WebUI seadistus SearXNG jaoks
+
+### 3.1 Docker Compose teenus
+
+Fail: `docker-compose.yml` – `open-webui` teenuse `environment` ploki kõige olulisemad read.
+
+```yaml
+open-webui:
+  image: ghcr.io/open-webui/open-webui:main
+  container_name: open-webui
+  restart: always
+  ports:
+    - "3000:8080"
+  volumes:
+    - open-webui_data:/app/backend/data
+    - ./open-webui-uploads:/app/backend/data/uploads
+    - ./open-webui-docs:/app/backend/data/docs
+  environment:
+    # Põhiseaded
+    - WEBUI_SECRET_KEY=ai_webui_secret_2026_change_me_to_random_string
+    - TZ=Europe/Tallinn
+    - OLLAMA_BASE_URL=http://ollama:11434
+
+    # RAG & embeddingud
+    - ENABLE_RAG_WEB_SEARCH=true
+    - RAG_EMBEDDING_ENGINE=ollama
+    - RAG_EMBEDDING_MODEL=nomic-embed-text:latest
+
+    # Web search SearXNG kaudu (OLULINE!)
+    - RAG_WEB_SEARCH_ENGINE=searxng
+    - SEARXNG_QUERY_URL=http://searxng:8080/search?q=<query>&format=json&categories=general,science
+    - RAG_WEB_SEARCH_RESULT_COUNT=3
+    - RAG_WEB_SEARCH_CONCURRENT_REQUESTS=5
+```
+
+**Oluline viga, mille parandasime:**
+alguses oli
+
+```yaml
+SEARXNG_QUERY_URL=http://searxng:8080/search?q=&categories=general,science
+```
+
+See ei sisestanud päringut ja SearXNG logisse ei tekkinud ühtegi `search` päringut.
+Õige on **`q=<query>&format=json`**.
+
+---
+
+## 4. Web search kasutamine Open WebUI-s
+
+### 4.1 Kuidas käivitada veebiotsing
+
+Vestluses:
+
+```text
+#web Milline ilm on täna Hiiumaal?
+```
+
+või
+
+```text
+#web Millised on viimased uudised Eestist?
+```
+
+`#web` sümbol sunnib Open WebUI’d kasutama RAG web search’i SearXNG kaudu.
+
+### 4.2 Kuidas kontrollida, kas SearXNG päriselt töötab
+
+1. Ava terminal:
+
+```bash
+docker logs -f searxng
+```
+
+2. Teises aknas Open WebUI-s tee `#web ...` päring.
+3. Kui integratsioon töötab, ilmuvad SearXNG logidesse uued read (vead / hoiatused / info) täpselt päringu ajal.
+Lisaks saab käsitsi testida:
+
+```bash
+curl "http://100.87.1.24:8888/search?q=hiiumaa&format=json" | jq '.results[0:2]'
+docker exec open-webui curl -s "http://searxng:8080/search?q=test&format=json" | jq '.results.title'
+```
+
+
+---
+
+## 5. Tüüpilised probleemid ja lahendused
+
+1. **Open WebUI vastused on „vana info“, SearXNG logi ei muutu**
+→ kontrolli, et `SEARXNG_QUERY_URL` sisaldab `<query>` ja `format=json`.
+2. **SearXNG logis DuckDuckGo CAPTCHA vead**
+→ keela DuckDuckGo mootorid `settings.yml`‑is (`disabled: true`).
+3. **SearXNG logis pidevalt `X-Forwarded-For nor X-Real-IP`**
+→ hoiatus; kuna `limiter: false`, võib seda ignoreerida.
+4. **Tahad rohkem / vähem veebi tulemusi**
+→ muuda Open WebUI env:
+
+```yaml
+- RAG_WEB_SEARCH_RESULT_COUNT=3  # 3–5 on mõistlik
+- RAG_WEB_SEARCH_CONCURRENT_REQUESTS=5  # 5–8, olenevalt koormusest
+```
+
+
+---
+
+## 6. Kiire „reset“ integratsioonile
+
+Kui tulevikus miski läheb segamini:
+
+```bash
+cd /opt/docker-compose/main
+
+# Stoppi ainult need kaks
+docker-compose stop open-webui searxng
+
+# Käivita SearXNG
+docker-compose up -d searxng
+
+# Kui SearXNG on terve:
+docker-compose up -d open-webui
+```
+
+Seejärel testi:
+
+```bash
+docker exec open-webui curl -s "http://searxng:8080/search?q=test&format=json" | jq '.results.title'
+```
+
+Kui see töötab, on SearXNG ja Open WebUI integratsioon korras.
+
+```
+<span style="display:none">[^1][^10][^11][^12][^13][^14][^15][^16][^17][^18][^19][^2][^20][^21][^3][^4][^5][^6][^7][^8][^9]</span>
+
+<div align="center">⁂</div>
+
+[^1]: docker-compose.yml
+[^2]: docker-compose.yml
+[^3]: image.jpg
+[^4]: image.jpg
+[^5]: docker-compose.yml
+[^6]: image.jpg
+[^7]: docker-compose.yml
+[^8]: image.jpg
+[^9]: paste.txt
+[^10]: docker-compose.yml
+[^11]: image.jpg
+[^12]: image.jpg
+[^13]: image.jpg
+[^14]: image.jpg
+[^15]: settings.yml
+[^16]: docker-compose.yml
+[^17]: settings.yml
+[^18]: limiter.toml
+[^19]: image.jpg
+[^20]: image.jpg
+[^21]: image.jpg```
+

+ 7 - 0
main/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 250 - 0
main/docker-compose.yml

@@ -0,0 +1,250 @@
+version: '3.8'
+
+services:
+
+  portainer:
+    image: portainer/portainer-ce:latest
+    container_name: portainer
+    restart: always
+    ports:
+      - "8000:8000"
+      - "9000:9000"
+      - "9443:9443"
+    volumes:
+      - /var/run/docker.sock:/var/run/docker.sock
+      - portainer_data:/data
+      - /backups/docker/portainer:/backups
+      - /etc/localtime:/etc/localtime
+    environment:
+      - TZ=Europe/Tallinn
+      - LANG=C.UTF-8
+    networks:
+      - ai_network
+
+  postgres:
+    image: kartoza/postgis:16
+    container_name: postgres_postgis
+    restart: always
+    ports:
+      - "5432:5432"
+    environment:
+      POSTGRES_USER: ai_user
+      POSTGRES_PASSWORD: ai_secure_pass_2026
+      POSTGRES_DB: research_db
+      POSTGRES_INITDB_ARGS: "-c shared_buffers=256MB -c max_connections=200"
+      PGDATA: /var/lib/postgresql/data/pgdata
+      TZ: Europe/Tallinn
+      LANG: C.UTF-8
+    mem_limit: 4g
+    volumes:
+      - postgres_data:/var/lib/postgresql/data
+      - ./init-db:/docker-entrypoint-initdb.d
+      - /backups/docker/postgres:/backups
+      - /etc/localtime:/etc/localtime
+    healthcheck:
+      test: ["CMD-SHELL", "pg_isready -U ai_user -d research_db"]
+      interval: 10s
+      timeout: 5s
+      retries: 5
+    networks:
+      - ai_network
+
+  mariadb:
+    image: mariadb:11
+    container_name: mariadb
+    restart: always
+    ports:
+      - "3306:3306"
+    environment:
+      MYSQL_ROOT_PASSWORD: ai_root_pass_2026
+      MYSQL_DATABASE: research_mariadb
+      MYSQL_USER: ai_mariadb_user
+      MYSQL_PASSWORD: ai_mariadb_pass_2026
+      TZ: Europe/Tallinn
+      LANG: C.UTF-8
+    mem_limit: 4g
+    volumes:
+      - mariadb_data:/var/lib/mysql
+      - /backups/docker/mariadb:/backups
+      - /etc/localtime:/etc/localtime
+    healthcheck:
+      test: ["CMD", "mariadb-admin", "ping", "-h", "localhost", "-uai_mariadb_user", "-pai_mariadb_pass_2026"]
+      interval: 10s
+      timeout: 5s
+      retries: 5
+    networks:
+      - ai_network
+
+  weaviate:
+    mem_limit: 4g
+    image: semitechnologies/weaviate:1.28.0
+    container_name: weaviate
+    restart: always
+    ports:
+      - "8080:8080"
+      - "50051:50051"
+    environment:
+      QUERY_DEFAULTS_LIMIT: 25
+      AUTHENTICATION_ANONYMOUS_ACCESS_ENABLED: 'true'
+      PERSISTENCE_DATA_PATH: '/var/lib/weaviate'
+      DEFAULT_VECTORIZER_MODULE: 'none'
+      CLUSTER_HOSTNAME: 'weaviate'
+      LANG: C.UTF-8
+    volumes:
+      - weaviate_data:/var/lib/weaviate
+      - /backups/docker/weaviate:/backups
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+
+  # Qdrant vektoriandmebaas (toetab Open WebUI)
+  qdrant:
+    mem_limit: 4g
+    image: qdrant/qdrant:v1.18.2
+    container_name: qdrant
+    restart: unless-stopped
+    ports:
+      - "6333:6333"  # REST API
+      - "6334:6334"  # gRPC API
+    environment:
+      TZ: Europe/Tallinn
+      LANG: C.UTF-8
+    volumes:
+      - qdrant_data:/qdrant/storage
+      - ./qdrant-config.yaml:/qdrant/config/production.yaml:ro
+      - /backups/docker/qdrant:/backups
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+    healthcheck:
+      test: ["CMD", "bash", "-c", "</dev/tcp/localhost/6333"]
+      interval: 30s
+      timeout: 10s
+      retries: 3
+      start_period: 10s
+
+  jupyter:
+    mem_limit: 8g
+    image: jupyter/datascience-notebook:python-3.11
+    container_name: jupyter
+    restart: always
+    ports:
+      - "8887:8888"
+    environment:
+      - JUPYTER_ENABLE_LAB=yes
+      - JUPYTER_TOKEN=ai_server_2026
+      - LANG=C.UTF-8
+      #- TZ=Europe/Tallinn
+    volumes:
+      - /data/docker/jupyter/notebooks:/home/jovyan/work
+      - /data/docker/jupyter/data:/home/jovyan/data
+      - jupyter_data:/home/jovyan/.jupyter
+      - /backups/docker/jupyter:/backups
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+    command: start-notebook.sh --NotebookApp.token='ai_server_2026' --NotebookApp.allow_root=True
+
+  rocm-pytorch:
+    image: rocm/pytorch:latest
+    container_name: rocm_pytorch
+    restart: always
+    ports:
+      - "8889:8888"
+      - "6006:6006"
+    environment:
+      - HSA_OVERRIDE_GFX_VERSION=11.5.1
+      - PYTORCH_ROCM_ARCH=gfx1151
+      - ROCM_HOME=/opt/rocm
+      - TZ=Europe/Tallinn
+      - LANG=C.UTF-8
+      - TORCH_ROCM_AOTRITON_ENABLE_EXPERIMENTAL=1
+    devices:
+      - /dev/kfd:/dev/kfd
+      - /dev/dri:/dev/dri
+    volumes:
+      - /data/docker/jupyter/pytorch-workspace:/workspace
+      - /data/docker/jupyter/models:/models
+      - /data/docker/jupyter/data:/data
+      - rocm_pytorch_data:/root/.cache
+      - /backups/docker/rocm-pytorch:/backups
+      - /etc/localtime:/etc/localtime
+    working_dir: /workspace
+    cap_add:
+      - SYS_PTRACE
+    security_opt:
+      - seccomp=unconfined
+    ipc: host
+    shm_size: 8G
+    group_add:
+      - video
+    networks:
+      - ai_network
+    command: >
+      bash -c "pip install jupyter notebook tensorboard transformers datasets huggingface_hub scikit-learn pandas psycopg2-binary &&
+      jupyter notebook --ip=0.0.0.0 --port=8888 --no-browser --allow-root --NotebookApp.token='ai_pytorch_2026'"
+
+  rag-api:
+    mem_limit: 4g
+    build:
+      context: /opt/docker-compose/main/Dockerfile/rag-api
+      dockerfile: Dockerfile
+    container_name: rag_api
+    restart: always
+    ports:
+      - "8072:8000"
+    environment:
+      LLAMA_CPP_URL: http://100.87.1.24:8070/completion
+      WEAVIATE_HOST: weaviate
+      WEAVIATE_HTTP_PORT: 8080
+      WEAVIATE_URL: http://weaviate:8080
+      WEAVIATE_CLASS: ScientificArticle
+      DB_HOST: postgres
+      DB_PORT: 5432
+      DB_NAME: pdf_research
+      DB_USER: osm
+      DB_PASSWORD: osm
+      OLLAMA_URL: http://100.87.1.24:11434
+      TZ: Europe/Tallinn
+      LANG: C.UTF-8
+      MARIADB_HOST: mariadb
+      MARIADB_PORT: 3306
+      MARIADB_DB: research_mariadb
+      MARIADB_USER: ai_mariadb_user
+      MARIADB_PASSWORD: ai_mariadb_pass_2026
+    volumes:
+      - /data/docker/rag-api/src:/app/src
+      - /backups/docker/rag-api:/backups
+      - /etc/localtime:/etc/localtime
+    depends_on:
+      - weaviate
+      - postgres
+    networks:
+      - ai_network
+    healthcheck:
+      test: ["CMD", "true"]
+      interval: 30s
+      timeout: 10s
+      retries: 3
+      start_period: 40s
+
+volumes:
+  portainer_data:
+    driver: local
+  postgres_data:
+    driver: local
+  weaviate_data:
+    driver: local
+  jupyter_data:
+    driver: local
+  rocm_pytorch_data:
+    driver: local
+  mariadb_data:
+    driver: local
+  qdrant_data:
+    external: true
+    name: qdrant_data
+
+networks:
+  ai_network:
+    driver: bridge

+ 11 - 0
main/init-db/01-create-openwebui-db.sql

@@ -0,0 +1,11 @@
+-- Loo Open WebUI andmebaas
+CREATE DATABASE openwebui_db;
+GRANT ALL PRIVILEGES ON DATABASE openwebui_db TO ai_user;
+
+-- Loo RAG API andmebaas
+CREATE DATABASE pdf_research;
+GRANT ALL PRIVILEGES ON DATABASE pdf_research TO ai_user;
+
+-- Loo kasutaja RAG API jaoks
+CREATE USER osm WITH PASSWORD 'osm';
+GRANT ALL PRIVILEGES ON DATABASE pdf_research TO osm;

+ 29 - 0
main/init-db/01-init-postgis.sql

@@ -0,0 +1,29 @@
+-- Loo lihtsalt UUID ilma extensionita
+CREATE TABLE articles (
+    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
+    title TEXT NOT NULL,
+    abstract TEXT,
+    content TEXT,
+    authors TEXT[],
+    published_date DATE,
+    doi TEXT UNIQUE,
+    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
+    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
+);
+
+CREATE TABLE article_embeddings (
+    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
+    article_id UUID NOT NULL REFERENCES articles(id) ON DELETE CASCADE,
+    embedding_model TEXT,
+    vector_data BYTEA,
+    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
+);
+
+-- Indeksid
+CREATE INDEX idx_articles_title ON articles USING GIN(to_tsvector('english', title));
+CREATE INDEX idx_articles_abstract ON articles USING GIN(to_tsvector('english', abstract));
+CREATE INDEX idx_article_embeddings_article_id ON article_embeddings(article_id);
+
+-- Õigused
+GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA public TO ai_user;
+GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA public TO ai_user;

+ 28 - 0
main/patches/patch_ollama_embeddings.py

@@ -0,0 +1,28 @@
+from pathlib import Path
+
+p = Path("/app/backend/open_webui/retrieval/utils.py")
+txt = p.read_text()
+
+# 1) /api/embed -> /api/embeddings
+txt = txt.replace("/api/embed", "/api/embeddings")
+
+# 2) asenda embeddingu plokk ühtse versiooniga
+old_block = """                data = await r.json()
+                if "embeddings" in data:
+                    return data["embeddings"]
+                else:
+                    raise Exception("Something went wrong :/")"""
+
+new_block = """                data = await r.json()
+                if "embeddings" in data:
+                    return data["embeddings"]
+                elif "embedding" in data:
+                    # Ollama: üksiku embeddingu vastus
+                    return [data["embedding"]]
+                else:
+                    raise Exception("Something went wrong :/")"""
+
+if old_block in txt:
+    txt = txt.replace(old_block, new_block)
+
+p.write_text(txt)

+ 11 - 0
main/qdrant-config.yaml

@@ -0,0 +1,11 @@
+storage:
+  # Optimeeri suurtele andmekogumitele
+  hnsw_ef_construct: 100  # Default: 100 (suurendades = täpsem, aeglasem indekseerimine)
+  hnsw_m: 16              # Default: 16 (suurendades = täpsem otsing, rohkem mälu)
+
+  # Mälu optimeerimine
+  on_disk: false          # Hoia vektorid RAM-is (kiirem, aga vajab rohkem mälu)
+  # on_disk: true         # Kui vektoreid on väga palju (>1M)
+
+service:
+  max_request_size_mb: 256  # Suurenda kui suur failide hulk

+ 9 - 0
main/run.sh

@@ -0,0 +1,9 @@
+#!/bin/bash
+
+docker-compose up -d
+
+# Install postgresql modules
+sleep 3
+bash scripts/install-pgvector.sh
+
+exit 0

+ 55 - 0
main/scripts/install-pgvector.sh

@@ -0,0 +1,55 @@
+# file: install-pgvector.sh
+
+#!/bin/bash
+
+echo "🔧 Paigaldame pgvector'i PostgreSQL konteineri sees..."
+
+docker exec postgres_postgis bash -c '
+apt-get update
+apt-get install -y build-essential postgresql-server-dev-16 git
+
+echo "pgvector paigaldus lõpetatud!"
+'
+
+docker exec postgres_postgis bash -c '
+apt-get install postgresql-16-pgvector
+echo "✓ Pgvector paigaldatud konteineri sees"
+'
+
+# Admin kasutaja lisamine
+docker exec -it postgres_postgis bash -c "
+  export PGPASSWORD='ai_secure_pass_2026' &&
+  psql -U ai_user -h localhost -d research_db -c \"
+  CREATE ROLE osm WITH LOGIN SUPERUSER CREATEDB CREATEROLE PASSWORD 'osm'\"
+"
+# PDF-de andmevbaasi loomine
+docker exec -it postgres_postgis bash -c "
+  export PGPASSWORD='ai_secure_pass_2026' &&
+  psql -U ai_user -h localhost -d research_db -c '
+  CREATE DATABASE pdf_research WITH OWNER = osm;'
+"
+# Laienduste lisamine
+docker exec -it postgres_postgis bash -c "
+  export PGPASSWORD='osm' &&
+  psql -U osm -h localhost -d pdf_research -c \"
+  CREATE EXTENSION IF NOT EXISTS postgis CASCADE;
+  CREATE EXTENSION IF NOT EXISTS pointcloud CASCADE;
+  CREATE EXTENSION IF NOT EXISTS pointcloud_postgis CASCADE;
+  CREATE EXTENSION IF NOT EXISTS fuzzystrmatch CASCADE;
+  CREATE EXTENSION IF NOT EXISTS postgis_tiger_geocoder CASCADE;
+  CREATE EXTENSION IF NOT EXISTS postgis_topology CASCADE;
+  CREATE EXTENSION IF NOT EXISTS postgis_raster CASCADE;
+  CREATE EXTENSION IF NOT EXISTS pgrouting CASCADE;
+  CREATE EXTENSION IF NOT EXISTS postgis_sfcgal CASCADE;
+  CREATE EXTENSION IF NOT EXISTS hstore CASCADE;
+  CREATE EXTENSION IF NOT EXISTS plpgsql CASCADE;
+  CREATE EXTENSION IF NOT EXISTS vector CASCADE;
+  SELECT * FROM pg_extension WHERE extname = 'vector';
+  \"
+"
+docker exec -it postgres_postgis bash -c "
+  export PGPASSWORD='osm' &&
+  psql -U osm -h localhost -d pdf_research -c '\dx'
+"
+
+echo "✓ Pgvector aktiveerimisel!"

+ 10 - 0
secondary/.env.example

@@ -0,0 +1,10 @@
+# secondary stack — keskkonnamuutujad
+# Kopeeri .env.example -> .env ja täida päris väärtused
+
+# Vaultwarden
+DOMAIN=https://ohmu.tail20e23.ts.net
+SIGNUPS_ALLOWED=false
+WEBSOCKET_ENABLED=true
+
+# Ajavöönd
+TZ=Europe/Tallinn

+ 8 - 0
secondary/LICENSE

@@ -0,0 +1,8 @@
+MIT License
+Copyright (c) <year> <copyright holders>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

+ 74 - 0
secondary/LOEMIND.md

@@ -0,0 +1,74 @@
+# Teisesed teenused (secondary) – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/secondary/`
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| it-tools | corentinth/it-tools | 9101 | IT tööriistad (JSON, base64, jne) |
+| vaultwarden | vaultwarden/server | 9080 | Paroolihaldur (Bitwarden) |
+| hop-web | apache/hop-web | 9102 | Apache Hop veebiliides |
+| hop-server | apache/hop | 9103 | Apache Hop server |
+
+## Docker käsud
+
+```bash
+# Käivita kõik
+docker-compose -f /opt/docker-compose/secondary/docker-compose.yml up -d
+
+# Peata kõik
+docker-compose -f /opt/docker-compose/secondary/docker-compose.yml down
+
+# Taaskäivita üks
+docker-compose -f /opt/docker-compose/secondary/docker-compose.yml restart vaultwarden
+
+# Logid (kõik)
+docker-compose -f /opt/docker-compose/secondary/docker-compose.yml logs -f
+
+# Logid (üks)
+docker-compose -f /opt/docker-compose/secondary/docker-compose.yml logs -f it-tools
+```
+
+## Üksikud konteinerid
+
+```bash
+# IT Tools
+docker logs it-tools
+
+# Vaultwarden (Bitwarden)
+docker logs vaultwarden
+
+# Apache Hop
+docker logs hop-web
+docker logs hop-server
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| IT Tools | http://100.87.1.24:9101 |
+| Vaultwarden | http://100.87.1.24:9080 |
+| Hop Web | http://100.87.1.24:9102 |
+| Hop Server | http://100.87.1.24:9103 |
+
+Kõik teenused on ainult kohalikul liidesel (`127.0.0.1`). Tailscale kaudu ligipääsuks:
+```bash
+sudo tailscale serve --bg --set-path /vault http://127.0.0.1:9080
+sudo tailscale serve --bg --set-path /hop http://127.0.0.1:9102
+```
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/data/docker/vaultwarden` | Vaultwarden andmed |
+| `/data/hop/projects` | Hop projektid |
+| `/backups/docker/vaultwarden` | Varukoopiad |
+| `/backups/docker/hop-web` | Varukoopiad |
+
+## Võrguinfo
+
+- Kõik konteinerid on `ai_network` peal
+- Teenused on eksponeeritud ainult kohalikule masinale

+ 3 - 0
secondary/README.md

@@ -0,0 +1,3 @@
+# secondary
+
+Docker-compose secondary failid

+ 7 - 0
secondary/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 101 - 0
secondary/docker-compose.yml

@@ -0,0 +1,101 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --set-path /vault http://127.0.0.1:9080
+# sudo tailscale serve --bg --set-path /vault off
+# sudo tailscale serve --bg --set-path /hop http://127.0.0.1:9102
+# sudo tailscale serve --bg --set-path /hop off
+
+# sudo tailscale serve --bg --https 8082 http://127.0.0.1:8082
+# sudo tailscale serve --https=8082 off
+# sudo tailscale serve --bg --https 9080 http://127.0.0.1:9080
+# sudo tailscale serve --https=9080 off
+# sudo tailscale serve --bg --https 9101 http://127.0.0.1:9101
+# sudo tailscale serve --https=9101 off
+# sudo tailscale serve --bg --https 9102 http://127.0.0.1:9102
+# sudo tailscale serve --https=9102 off
+# sudo tailscale serve --bg --https 9103 http://127.0.0.1:9103
+# sudo tailscale serve --https=9103 off
+
+# sudo tailscale serve status
+# Kõikide ühenduste kustutamine: sudo tailscale serve --bg off
+# `tailscale serve --help` for usage info
+
+
+services:
+  it-tools:
+    image: corentinth/it-tools:latest
+    container_name: it-tools
+    restart: unless-stopped
+    ports:
+      - "127.0.0.1:9101:80"
+    environment:
+      - LANG=C.UTF-8
+    volumes:
+      - /etc/localtime:/etc/localtime:ro
+    networks:
+      - ai_network
+
+  vaultwarden:
+    image: vaultwarden/server:latest
+    container_name: vaultwarden
+    restart: unless-stopped
+    environment:
+      # asenda oma domeeniga või jäta kommenteerituks kui kasutad ainult LAN-i
+      DOMAIN: "https://ohmu.tail20e23.ts.net"
+      SIGNUPS_ALLOWED: "false"
+      WEBSOCKET_ENABLED: "true"
+    volumes:
+      - /data/docker/vaultwarden:/data
+      - /data/docker/vaultwarden/nginx-vaultwarden.conf:/etc/nginx/nginx.conf:ro
+      - /backups/docker/vaultwarden:/backups
+      - /etc/localtime:/etc/localtime:ro
+    ports:
+      - "127.0.0.1:9080:80"
+    networks:
+      - ai_network
+
+  hop-web:
+    image: apache/hop-web:latest
+    container_name: hop-web
+    restart: unless-stopped
+    environment:
+      TZ: "Europe/Tallinn"
+      HOP_SERVER_HOSTNAME: "hop-server"
+      HOP_SERVER_PORT: "8181"
+      HOP_PROJECT_NAME: "default"
+      HOP_PROJECT_FOLDER: "/files"
+    ports:
+      - "127.0.0.1:9102:8080"
+    volumes:
+      - /data/hop/projects:/files
+      - /backups/docker/hop-web:/backups
+      - /etc/localtime:/etc/localtime:ro
+    networks:
+      - ai_network
+
+  hop-server:
+    image: apache/hop:latest
+    container_name: hop-server
+    restart: unless-stopped
+    environment:
+      TZ: "Europe/Tallinn"
+      HOP_SERVER_HOSTNAME: "0.0.0.0"
+      HOP_SERVER_PORT: "8181"
+      HOP_PROJECT_NAME: "default"
+      HOP_PROJECT_FOLDER: "/files"
+      HOP_ENVIRONMENT_NAME: "dev"
+      HOP_ENVIRONMENT_CONFIG_FILE_NAME_PATHS: "/files/dev-config.json"
+      HOP_RUN_CONFIG: "local"
+    ports:
+      - "127.0.0.1:9103:8181"
+    volumes:
+      - /data/hop/projects:/files
+      - /backups/docker/hop-server:/backups
+      - /etc/localtime:/etc/localtime:ro
+    networks:
+      - ai_network
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 10 - 0
secondary/run.sh

@@ -0,0 +1,10 @@
+#!/bin/bash
+
+docker-compose up -d
+sleep 10
+#docker-compose stop it-tools
+docker-compose stop vaultwarden
+docker-compose stop hop-web
+docker-compose stop hop-server
+
+exit 0

+ 65 - 0
third/R/r-studio/r-studio/LOEMIND.md

@@ -0,0 +1,65 @@
+# RStudio – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/R/r-studio/r-studio/`
+
+RStudio Server – veebipõhine R arenduskeskkond.
+
+## Docker käsud
+
+```bash
+# Käivita
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml up -d
+
+# Peata
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml down
+
+# Taaskäivita
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml restart
+
+# Logid
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml logs -f
+
+# Uuenda
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml pull
+docker-compose -f /opt/docker-compose/third/R/r-studio/r-studio/docker-compose.yml up -d
+```
+
+## Üksikud konteinerid
+
+```bash
+docker logs shiny-r-studio
+docker restart shiny-r-studio
+docker exec -it shiny-r-studio /bin/bash
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| RStudio | http://100.87.1.24:8012 |
+
+Autentimine on välja lülitatud (`DISABLE_AUTH=true`).
+
+## R pakettide paigaldamine
+
+RStudios saad pakette paigaldada konsoolis:
+```r
+install.packages("tidyverse")
+install.packages("shiny")
+```
+
+Püsivad paketid salvestatakse Docker volume'i `shiny_r-packages`.
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| Docker volume: `shiny_r-packages` | R paketid |
+| Docker volume: `shiny_r-studio-home` | RStudio kasutaja kodukaust |
+| Docker volume: `shiny_paberkrohv-apps` | Shiny rakendused |
+| `/backups/docker/R` | Varukoopiad |
+
+## Võrguinfo
+
+- Konteiner on `ai_network` peal
+- Port 8012 on avatud kõikidel liidestel

+ 66 - 0
third/R/r-studio/r-studio/LOEMIND.txt

@@ -0,0 +1,66 @@
+# !!!!!!!!!!
+
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+apt-get update && \
+apt-get install -y --no-install-recommends \
+libpq-dev libcairo2-dev libxt-dev libxml2 libxml2-dev \
+libglpk-dev imagemagick'
+
+# imageJ installimine
+# Lae all Fiji.app https://imagej.net/Fiji/Downloads
+fiji_name=fiji-linux64-20170530.zip
+wget https://downloads.imagej.net/fiji/Life-Line/${fiji_name}
+unzip ${fiji_name}
+ln -s Fiji.app/ImageJ-linux64 ImageJ-linux64
+
+# test https://imagej.net/Scripting_Headless
+./ImageJ-linux64 --ij2 --headless
+
+
+# Proovi käsk piltide konvertimiseks
+ImageJ-linux64  --headless --console -macro ./ijm/RunBatch.ijm 'img/'
+
+
+## -------------- vana versioon ------------------
+# Kui V8 shiny's ei tööta
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+printf "deb http://archive.debian.org/debian/ jessie main\ndeb-src http://archive.debian.org/debian/ jessie main\ndeb http://security.debian.org/debian-security/ jessie/updates main\ndeb-src http://security.debian.org/debian-security/ jessie/updates main" > /etc/apt/sources.list && \
+apt-get update && \
+apt-get install -y --no-install-recommends  --force-yes \
+libv8-dev libnlopt-dev libgeos-dev'
+
+# V8 paketi installimiseks Ubuntu 20.04 korral arvutis uthp
+sudo apt-get install libssl1.1=1.1.1f-1ubuntu2
+sudo apt-get install libnode-dev
+#
+
+
+## Täiendused !!!!
+
+docker exec -ti shiny-r-studio bash -c "
+  apt update
+  apt -y upgrade
+  apt install -y iputils-ping libpq-dev postgresql-client build-essential pkg-config libssl-dev \
+  libcairo2 libcairo2-dev libxt-dev libx11-dev libfreetype6-dev libharfbuzz-dev libpng-dev \
+  libjpeg-dev libtiff5-dev nano netcat-traditional iproute2 libxml2-dev curl zlib1g-dev libicu-dev \
+  libreadline-dev libblas-dev liblapack-dev gfortran libglpk-dev cmake ninja-build \
+  libbz2-dev liblzma-dev libpcre2-dev libcurl4-openssl-dev libsqlite3-dev libspatialite-dev \
+  gdal-bin libgdal-dev libgeos-dev libgeos++-dev proj-bin libproj-dev libudunits2-dev   
+  apt -y autoremove
+"
+
+docker exec -ti shiny-r-studio bash -c "
+# units (vajab libudunits2-dev)
+sudo bash -lc 'R -q -e \"install.packages(\"units\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# sf (kasutab GDAL/GEOS/PROJ)
+sudo bash -lc 'R -q -e \"install.packages(\"sf\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# lwgeom (vajab liblwgeom-dev + sf)
+sudo bash -lc 'R -q -e \"install.packages(\"lwgeom\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# lõpuks stplanr
+sudo bash -lc 'R -q -e \"install.packages(\"stplanr\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+"
+
+

+ 21 - 0
third/R/r-studio/r-studio/cleanup.sh

@@ -0,0 +1,21 @@
+#!/bin/bash
+
+# Copyright 2016 - 2020 Crunchy Data Solutions, Inc.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+echo "Cleaning up..."
+
+#docker-compose -p "shiny" -f docker-compose.yml down
+docker-compose down
+
+exit 0

+ 41 - 0
third/R/r-studio/r-studio/docker-compose.yml

@@ -0,0 +1,41 @@
+version: '3.4'
+# https://rocker-project.org/images/versioned/rstudio.html
+# https://github.com/rocker-org/rocker-versioned2
+
+services:
+  r-studio:
+    restart: always
+    image: rocker/rstudio:4.0.5
+    container_name: shiny-r-studio
+    ports:
+      - 8012:8787
+    environment:
+      #- USER=ardo
+      #- PASSWORD=tRJMAHLfDSoYWrGufz9O
+      - DISABLE_AUTH=true
+      - TZ=Europe/Tallinn
+      #- ADD=shiny
+    volumes:
+      - r-packages:/usr/local/lib/R/site-library
+      - r-studio-home:/home/rstudio/rstudio
+      - shiny_paberkrohv-apps:/home/rstudio/shiny-apps
+      - /backups/docker/R:/backups
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+
+volumes:
+  r-packages:
+    name: shiny_r-packages
+    external: true
+  shiny_paberkrohv-apps:
+    name: shiny_paberkrohv-apps
+    external: true
+  r-studio-home:
+    name: shiny_r-studio-home
+    external: true
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 45 - 0
third/R/r-studio/r-studio/run.sh

@@ -0,0 +1,45 @@
+#!/bin/bash
+
+# Copyright 2016 - 2020 Crunchy Data Solutions, Inc.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+docker-compose up -d
+
+sleep 5
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+useradd -m -s /bin/bash ardo; \
+echo "ardo:tRJMAHLfDSoYWrGufz9O" | chpasswd; \
+'
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+apt-get update && \
+apt-get install -y --no-install-recommends \
+libpq-dev libcairo2-dev libxt-dev libxml2 libxml2-dev \
+libglpk-dev imagemagick'
+## Täiendused !!!!
+docker exec -ti shiny-r-studio bash -c "
+  apt update
+  apt -y upgrade
+  apt install -y iputils-ping libpq-dev postgresql-client build-essential pkg-config libssl-dev \
+  libcairo2 libcairo2-dev libxt-dev libx11-dev libfreetype6-dev libharfbuzz-dev libpng-dev \
+  libjpeg-dev libtiff5-dev nano netcat-traditional iproute2 libxml2-dev curl zlib1g-dev libicu-dev \
+  libreadline-dev libblas-dev liblapack-dev gfortran libglpk-dev cmake ninja-build \
+  libbz2-dev liblzma-dev libpcre2-dev libcurl4-openssl-dev libsqlite3-dev libspatialite-dev \
+  gdal-bin libgdal-dev libgeos-dev libgeos++-dev proj-bin libproj-dev libudunits2-dev
+  apt -y autoremove
+"
+
+exit 0

+ 13 - 0
third/R/r-studio/r-studio/scripts/cron.sh

@@ -0,0 +1,13 @@
+#!/bin/bash
+# Sünkroonimise skripti lisamine cron-i.
+
+echo "Sünkroonimine ........"
+
+cont_name=shiny-r-studio
+docker exec -t -u 0 ${cont_name} sh -c ' \
+chmod 0777 -R /home/ardo/.R/gargle/gargle-oauth/; \
+cd /home/ardo/rstudio/filipiinid/postgres_googlesheet_sync; \
+chmod 0777 -R ../postgres_googlesheet_sync/; \
+ls -la; \
+Rscript sync_files/myfitness_sync.R;
+'

+ 70 - 0
third/R/shiny/paberkrohv/LOEMIND.md

@@ -0,0 +1,70 @@
+# Shiny Paberkrohv – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/R/shiny/paberkrohv/`
+
+Shiny Server – R veebirakenduste hostimiseks.
+
+## Docker käsud
+
+```bash
+# Käivita
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml up -d
+
+# Peata
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml down
+
+# Taaskäivita
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml restart
+
+# Logid
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml logs -f
+
+# Uuenda
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml pull
+docker-compose -f /opt/docker-compose/third/R/shiny/paberkrohv/docker-compose.yml up -d
+```
+
+## Üksikud konteinerid
+
+```bash
+docker logs shiny-paberkrohv
+docker restart shiny-paberkrohv
+docker exec -it shiny-paberkrohv /bin/bash
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| Shiny Server | http://100.87.1.24:8013 |
+
+## Shiny rakenduse lisamine
+
+Shiny rakendused paigutatakse volume'i `shiny_paberkrohv-apps`. Iga alamkataloog on omaette rakendus:
+
+```
+/srv/shiny-server/
+├── app1/
+│   ├── ui.R
+│   └── server.R
+├── app2/
+│   ├── ui.R
+│   └── server.R
+```
+
+Rakendused on kohe nähtavad aadressil http://100.87.1.24:8013/app1/
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| Docker volume: `shiny_paberkrohv-apps` | Shiny rakendused |
+| Docker volume: `shiny_paberkrohv-logs` | Logid |
+| Docker volume: `shiny_paberkrohv-conf` | Shiny seadistus |
+| Docker volume: `shiny_r-packages` | R paketid (jagatud RStudioga) |
+| `/backups/docker/R` | Varukoopiad |
+
+## Võrguinfo
+
+- Konteiner on `ai_network` peal
+- Port 8013 on avatud kõikidel liidestel

+ 39 - 0
third/R/shiny/paberkrohv/LOEMIND.txt

@@ -0,0 +1,39 @@
+# !!!!!!!!!!
+
+
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-paberkrohv
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+apt-get update && \
+apt-get install -y --no-install-recommends \
+libpq-dev libcairo2-dev libxt-dev libxml2 libxml2-dev \
+libglpk-dev imagemagick'
+
+
+## -------------- vana versioon ------------------
+# Kui V8 shiny's ei tööta
+cont_name=shiny-paberkrohv
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+printf "deb http://archive.debian.org/debian/ jessie main\ndeb-src http://archive.debian.org/debian/ jessie main\ndeb http://security.debian.org/debian-security/ jessie/updates main\ndeb-src http://security.debian.org/debian-security/ jessie/updates main" > /etc/apt/sources.list && \
+apt-get update && \
+apt-get install -y --no-install-recommends  --force-yes \
+libv8-dev'
+
+# V8 paketi installimiseks Ubuntu 20.04 korral arvutis uthp
+sudo apt-get install libssl1.1=1.1.1f-1ubuntu2
+sudo apt-get install libnode-dev
+#
+
+## ---------------------------------------------
+## Ühistransport + fotodelt kujundi arvutamin
+docker exec -ti shiny-paberkrohv bash -c "
+  apt update
+  apt -y upgrade
+  apt install -y iputils-ping libpq-dev postgresql-client build-essential pkg-config libssl-dev \
+  libcairo2 libcairo2-dev libxt-dev libx11-dev libfreetype6-dev libharfbuzz-dev libpng-dev \
+  libjpeg-dev libtiff5-dev nano netcat-traditional iproute2 libxml2-dev curl zlib1g-dev libicu-dev \
+  libreadline-dev libblas-dev liblapack-dev gfortran libglpk-dev cmake ninja-build \
+  libbz2-dev liblzma-dev libpcre2-dev libcurl4-openssl-dev libsqlite3-dev libspatialite-dev \
+  gdal-bin libgdal-dev libgeos-dev libgeos++-dev proj-bin libproj-dev libudunits2-dev 
+  apt -y autoremove
+"

+ 21 - 0
third/R/shiny/paberkrohv/cleanup.sh

@@ -0,0 +1,21 @@
+#!/bin/bash
+
+# Copyright 2016 - 2020 Crunchy Data Solutions, Inc.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+echo "Cleaning up..."
+
+docker-compose down
+
+
+exit 0

+ 41 - 0
third/R/shiny/paberkrohv/docker-compose.yml

@@ -0,0 +1,41 @@
+version: '3.4'
+services:
+  paberkrohv:
+    restart: always
+    image: rocker/shiny:4.0.5
+    container_name: shiny-paberkrohv
+    environment:
+      - TZ=Europe/Tallinn
+    volumes:
+      - r-packages:/usr/local/lib/R/site-library
+      - paberkrohv-apps:/srv/shiny-server
+      - paberkrohv-logs:/var/log
+      - paberkrohv-conf:/etc/shiny-server
+      - /backups/docker/R:/backups
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+    ports:
+      - 8013:3838
+
+volumes:
+  r-packages:
+    name: shiny_r-packages
+    external: true
+  paberkrohv-apps:
+    name: shiny_paberkrohv-apps
+    external: true
+  paberkrohv-conf:
+    name: shiny_paberkrohv-conf
+    external: true
+  paberkrohv-logs:
+    name: shiny_paberkrohv-logs
+    external: true
+  r-studio-home:
+    name: shiny_r-studio-home
+    external: true
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 39 - 0
third/R/shiny/paberkrohv/run.sh

@@ -0,0 +1,39 @@
+#!/bin/bash
+
+# Copyright 2016 - 2020 Crunchy Data Solutions, Inc.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+docker-compose up -d
+
+sleep 2
+
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-paberkrohv
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+apt-get update && \
+apt-get install -y --no-install-recommends \
+libpq-dev libcairo2-dev libxt-dev libxml2'
+
+docker exec -ti shiny-paberkrohv bash -c "
+  apt update
+  apt -y upgrade
+  apt install -y iputils-ping libpq-dev postgresql-client build-essential pkg-config libssl-dev \
+  libcairo2 libcairo2-dev libxt-dev libx11-dev libfreetype6-dev libharfbuzz-dev libpng-dev \
+  libjpeg-dev libtiff5-dev nano netcat-traditional iproute2 libxml2-dev curl zlib1g-dev libicu-dev \
+  libreadline-dev libblas-dev liblapack-dev gfortran libglpk-dev cmake ninja-build \
+  libbz2-dev liblzma-dev libpcre2-dev libcurl4-openssl-dev libsqlite3-dev libspatialite-dev \
+  gdal-bin libgdal-dev libgeos-dev libgeos++-dev proj-bin libproj-dev libudunits2-dev
+  apt -y autoremove
+"
+
+exit 0

+ 82 - 0
third/browserless/LOEMIND.md

@@ -0,0 +1,82 @@
+# Brauseriteenused (browserless) – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/browserless/`
+
+Selenium Grid veebibrauserite automaatseks juhtimiseks + Browserless server.
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| selenium-hub | selenium/hub | 4444 | Selenium Grid keskus |
+| selenium-chrome | selenium/node-chrome | 7900 | Chrome brauser Node |
+| selenium-firefox | selenium/node-firefox | 7901 | Firefox brauser Node |
+| browserless | browserless/chrome | 3001 | Browserless Chrome API |
+
+## Docker käsud
+
+```bash
+# Käivita kõik
+docker-compose -f /opt/docker-compose/third/browserless/docker-compose.yml up -d
+
+# Peata kõik
+docker-compose -f /opt/docker-compose/third/browserless/docker-compose.yml down
+
+# Taaskäivita üks
+docker-compose -f /opt/docker-compose/third/browserless/docker-compose.yml restart selenium-chrome
+
+# Logid
+docker-compose -f /opt/docker-compose/third/browserless/docker-compose.yml logs -f
+```
+
+## Üksikud konteinerid
+
+```bash
+# Selenium Grid
+docker logs selenium-hub
+docker logs selenium-chrome
+docker logs selenium-firefox
+
+# Browserless
+docker logs browserless_browserless_1
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| Selenium Grid | http://100.87.1.24:4444 |
+| Chrome VNC | http://100.87.1.24:7900 (VNC vaatamiseks) |
+| Firefox VNC | http://100.87.1.24:7901 (VNC vaatamiseks) |
+| Browserless | http://100.87.1.24:3001 |
+
+## Selenium kasutamine (Python)
+
+```python
+from selenium import webdriver
+from selenium.webdriver.chrome.options import Options
+
+options = Options()
+options.add_argument("--headless=new")
+driver = webdriver.Remote(
+    command_executor="http://100.87.1.24:4444/wd/hub",
+    options=options,
+)
+driver.get("https://example.com")
+print(driver.title)
+driver.quit()
+```
+
+## Browserless kasutamine
+
+```bash
+curl -X POST http://100.87.1.24:3001/content \
+  -H "Content-Type: application/json" \
+  -d '{"url": "https://example.com"}'
+```
+
+## Võrguinfo
+
+- Kõik konteinerid on `ai_network` peal
+- Chrome ja Firefox kasutavad jagatud mälu (shm_size: 2gb)
+- Firefox profiil: `/tmp/firefox-profile`

+ 66 - 0
third/browserless/LOEMIND.txt

@@ -0,0 +1,66 @@
+# !!!!!!!!!!
+
+# Uue rocker image juures vajalikud installimised.
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+apt-get update && \
+apt-get install -y --no-install-recommends \
+libpq-dev libcairo2-dev libxt-dev libxml2 libxml2-dev \
+libglpk-dev imagemagick'
+
+# imageJ installimine
+# Lae all Fiji.app https://imagej.net/Fiji/Downloads
+fiji_name=fiji-linux64-20170530.zip
+wget https://downloads.imagej.net/fiji/Life-Line/${fiji_name}
+unzip ${fiji_name}
+ln -s Fiji.app/ImageJ-linux64 ImageJ-linux64
+
+# test https://imagej.net/Scripting_Headless
+./ImageJ-linux64 --ij2 --headless
+
+
+# Proovi käsk piltide konvertimiseks
+ImageJ-linux64  --headless --console -macro ./ijm/RunBatch.ijm 'img/'
+
+
+## -------------- vana versioon ------------------
+# Kui V8 shiny's ei tööta
+cont_name=shiny-r-studio
+docker exec -ti -u 0 ${cont_name} sh -c ' \
+printf "deb http://archive.debian.org/debian/ jessie main\ndeb-src http://archive.debian.org/debian/ jessie main\ndeb http://security.debian.org/debian-security/ jessie/updates main\ndeb-src http://security.debian.org/debian-security/ jessie/updates main" > /etc/apt/sources.list && \
+apt-get update && \
+apt-get install -y --no-install-recommends  --force-yes \
+libv8-dev libnlopt-dev libgeos-dev'
+
+# V8 paketi installimiseks Ubuntu 20.04 korral arvutis uthp
+sudo apt-get install libssl1.1=1.1.1f-1ubuntu2
+sudo apt-get install libnode-dev
+#
+
+
+## Täiendused !!!!
+
+docker exec -ti shiny-r-studio bash -c "
+  apt update
+  apt -y upgrade
+  apt install -y iputils-ping libpq-dev postgresql-client build-essential pkg-config libssl-dev \
+  libcairo2 libcairo2-dev libxt-dev libx11-dev libfreetype6-dev libharfbuzz-dev libpng-dev \
+  libjpeg-dev libtiff5-dev nano netcat-traditional iproute2 libxml2-dev curl zlib1g-dev libicu-dev \
+  libreadline-dev libblas-dev liblapack-dev gfortran libglpk-dev cmake ninja-build \
+  libbz2-dev liblzma-dev libpcre2-dev libcurl4-openssl-dev libsqlite3-dev libspatialite-dev \
+  gdal-bin libgdal-dev libgeos-dev libgeos++-dev proj-bin libproj-dev libudunits2-dev   
+  apt -y autoremove
+"
+
+docker exec -ti shiny-r-studio bash -c "
+# units (vajab libudunits2-dev)
+sudo bash -lc 'R -q -e \"install.packages(\"units\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# sf (kasutab GDAL/GEOS/PROJ)
+sudo bash -lc 'R -q -e \"install.packages(\"sf\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# lwgeom (vajab liblwgeom-dev + sf)
+sudo bash -lc 'R -q -e \"install.packages(\"lwgeom\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+# lõpuks stplanr
+sudo bash -lc 'R -q -e \"install.packages(\"stplanr\", repos=\"https://cloud.r-project.org\", Ncpus=parallel::detectCores())\"'
+"
+
+

+ 7 - 0
third/browserless/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 87 - 0
third/browserless/docker-compose.yml

@@ -0,0 +1,87 @@
+version: '3.4'
+
+services:
+  selenium-hub:
+    image: selenium/hub:4.41.0
+    container_name: selenium-hub
+    ports:
+      - "4444:4444"   # WebDriver API
+      - "4442:4442"   # event bus publish
+      - "4443:4443"   # event bus subscribe
+    environment:
+      - SE_OPTS=--log-level INFO
+      - TZ=Europe/Tallinn
+      - LANG=C.UTF-8
+    volumes:
+      - /etc/localtime:/etc/localtime
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  selenium-chrome:
+    image: selenium/node-chrome:4.41.0
+    container_name: selenium-chrome
+    depends_on:
+      - selenium-hub
+    environment:
+      - SE_EVENT_BUS_HOST=selenium-hub
+      - SE_EVENT_BUS_PUBLISH_PORT=4442
+      - SE_EVENT_BUS_SUBSCRIBE_PORT=4443
+      - SE_NODE_MAX_SESSIONS=4
+      - SE_NODE_OVERRIDE_MAX_SESSIONS=true
+      - SE_VNC_NO_PASSWORD=1   # Disable VNC password
+      - TZ=Europe/Tallinn
+      - LANG=C.UTF-8
+    volumes:
+      - /etc/localtime:/etc/localtime
+    shm_size: 2gb
+    restart: unless-stopped
+    ports:
+      - "7900:7900"
+    networks:
+      - ai_network
+
+  selenium-firefox:
+    image: selenium/node-firefox:4.41.0
+    container_name: selenium-firefox
+    depends_on:
+      - selenium-hub
+    environment:
+      - SE_EVENT_BUS_HOST=selenium-hub
+      - SE_EVENT_BUS_PUBLISH_PORT=4442
+      - SE_EVENT_BUS_SUBSCRIBE_PORT=4443
+      - SE_NODE_MAX_SESSIONS=4
+      - SE_NODE_OVERRIDE_MAX_SESSIONS=true
+      - SE_VNC_NO_PASSWORD=1   # Disable VNC password
+      - TZ=Europe/Tallinn
+      - LANG=C.UTF-8
+    volumes:
+      - /etc/localtime:/etc/localtime
+      # sudo cp -r ~/.mozilla/firefox/xxxx.default /tmp/firefox-profile
+      - /tmp/firefox-profile:/home/seluser/firefox-profile:ro
+    shm_size: 2gb
+    restart: unless-stopped
+    ports:
+      - "7901:7900"
+    networks:
+      - ai_network
+
+
+  browserless:
+    image: browserless/chrome
+    restart: unless-stopped
+    ports:
+      - "3001:3000"
+    environment:
+      - MAX_CONCURRENT_SESSIONS=5
+      - CONNECTION_TIMEOUT=60000
+      - TZ=Europe/Tallinn
+    volumes:
+      - /etc/localtime:/etc/localtime
+    networks:
+      - ai_network
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 6 - 0
third/browserless/run.sh

@@ -0,0 +1,6 @@
+#!/bin/bash
+
+docker-compose up -d
+sleep 5
+
+exit 0

+ 23 - 0
third/drupal/arilix/LOEMIND.txt

@@ -0,0 +1,23 @@
+
+apt update
+apt -y install curl git unzip vim wget && \
+apt-get clean
+# Drupali tuuma install
+composer install
+# To see which versions of Drupal core are available, use this command
+composer show drupal/recommended-project --all
+#Check for available Drupal core and module updates:
+composer outdated drupal/*
+# All of your modules and themes can be updated along with Drupal core via:
+composer update
+
+
+# Mooduli install
+php -d memory_limit=-1 `which composer` require 'drupal/masquerade' --update-no-dev  --update-with-all-dependencies
+# SMTP
+php -d memory_limit=-1 `which composer` require 'phpmailer/phpmailer' --update-no-dev
+php -d memory_limit=-1 `which composer` require 'drupal/smtp' --update-no-dev --update-with-all-dependencies
+# Theme
+php -d memory_limit=-1 `which composer` require 'drupal/d8w3css' --update-no-dev --update-with-all-dependencies
+#composer remove 'drupal/d8w3css' --update-with-dependencies
+

+ 7 - 0
third/drupal/arilix/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 19 - 0
third/drupal/arilix/config/arilix.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 57 - 0
third/drupal/arilix/docker-compose.yml

@@ -0,0 +1,57 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --https 8004 http://127.0.0.1:8004
+# sudo tailscale serve --https=8004 off
+# sudo tailscale serve status
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-arilix
+    hostname: bussikeskus
+    environment:
+      - TS_AUTHKEY=tskey-auth-kHqg75riq221CNTRL-jpYwnjgj9M6VobSftoDGM6sqvaD8jiDi
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/arilix.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: registry.odamus.com/drupal/drupal_7_rong:latest
+    container_name: drupal_arilix
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    #ports:
+    #  - "127.0.0.1:8004:80"
+    volumes:
+      - html:/var/www/html
+      - backups:/root/drush-backups
+      - /backups/docker/drupal/arilix:/backups
+      - /etc/localtime:/etc/localtime
+    #networks:
+    #  - ai_network
+    restart: unless-stopped
+
+volumes:
+  html:
+    name: 'drupal_arilix-html'
+    driver: local
+  backups:
+    name: 'drupal_arilix-backups'
+    driver: local
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 6 - 0
third/drupal/arilix/run.sh

@@ -0,0 +1,6 @@
+#!/bin/bash
+
+docker-compose up -d
+
+exit 0
+

二進制
third/drupal/arilix/xxx/bussikeskus.tar.gz


+ 19 - 0
third/drupal/bussikeskus/config/bussikeskus.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 50 - 0
third/drupal/bussikeskus/docker-compose.yml

@@ -0,0 +1,50 @@
+version: "3.9"
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-bussikeskus
+    hostname: bussikeskus-ohmu
+    environment:
+      - TS_AUTHKEY=tskey-auth-k1fycT38sK11CNTRL-8qi5GExmmdhJNghogtHfdhxVfbmc1zqjJ
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/bussikeskus.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+      - LANG=C.UTF-8
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: registry.odamus.com/drupal/drupal_7_rong:latest
+    container_name: drupal_bussikeskus
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    volumes:
+      - html:/var/www/html
+      - backups:/root/drush-backups
+      - /backups/docker/drupal/bussikeskus:/backups
+      - /etc/localtime:/etc/localtime
+    restart: unless-stopped
+
+volumes:
+  html:
+    name: drupal_bussikeskus-html
+    driver: local
+  backups:
+    name: drupal_bussikeskus-backups
+    driver: local
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 36 - 0
third/drupal/bussikeskus/sync_from_arilix.sh

@@ -0,0 +1,36 @@
+#!/usr/bin/env bash
+# =============================================================================
+# Arilix (production) -> ohmu (test): www_arilix andmebaasi + Drupali HTML
+# Välja arvatud settings.php (ohmu oma jääb alles)
+# Käivita root õigustega: sudo bash sync_from_arilix.sh
+# =============================================================================
+set -e
+
+ARILIX="root@100.74.36.86"
+ARILIX_MARIADB_PASS="JnBWLj921al3LXeQWAEA"
+OHMU_MARIADB_PASS="ai_root_pass_2026"
+ARILIX_HTML="/opt/drupal/bussikeskus/html"
+OHMU_HTML="/var/lib/docker/volumes/drupal_bussikeskus-html/_data"
+
+echo "=== $(date): Alustan sünkroonimist ==="
+
+# 1. MariaDB: dump arilixist ja import ohmu-sse
+echo "[1/3] MariaDB: dump arilix www_arilix -> ohmu mariadb ..."
+ssh "$ARILIX" "docker exec mysqldb mariadb-dump -u root -p\"$ARILIX_MARIADB_PASS\" --single-transaction www_arilix" \
+  | docker exec -i mariadb mariadb -u root -p"$OHMU_MARIADB_PASS" www_arilix 2>/dev/null
+echo "  DB sünkroonitud."
+
+# 2. Rsync Drupali HTML (v.a settings.php)
+echo "[2/3] Rsync: arilix HTML -> ohmu (v.a settings.php) ..."
+rsync -av --delete --exclude="settings.php" -e "ssh" \
+  "$ARILIX:$ARILIX_HTML/" \
+  "$OHMU_HTML/"
+echo "  HTML sünkroonitud."
+
+# 3. Tühjenda Drupali puhver
+echo "[3/3] Drupali puhvri tühjendamine..."
+docker exec drupal_bussikeskus sh -c "rm -rf /var/www/html/sites/default/files/cache/*" 2>/dev/null || true
+echo "  Puhver tühjendatud."
+
+echo ""
+echo "=== $(date): Sünkroonimine valmis ==="

+ 23 - 0
third/drupal/merbond/LOEMIND.txt

@@ -0,0 +1,23 @@
+
+apt update
+apt -y install curl git unzip vim wget && \
+apt-get clean
+# Drupali tuuma install
+composer install
+# To see which versions of Drupal core are available, use this command
+composer show drupal/recommended-project --all
+#Check for available Drupal core and module updates:
+composer outdated drupal/*
+# All of your modules and themes can be updated along with Drupal core via:
+composer update
+
+
+# Mooduli install
+php -d memory_limit=-1 `which composer` require 'drupal/masquerade' --update-no-dev  --update-with-all-dependencies
+# SMTP
+php -d memory_limit=-1 `which composer` require 'phpmailer/phpmailer' --update-no-dev
+php -d memory_limit=-1 `which composer` require 'drupal/smtp' --update-no-dev --update-with-all-dependencies
+# Theme
+php -d memory_limit=-1 `which composer` require 'drupal/d8w3css' --update-no-dev --update-with-all-dependencies
+#composer remove 'drupal/d8w3css' --update-with-dependencies
+

+ 7 - 0
third/drupal/merbond/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 19 - 0
third/drupal/merbond/config/merbond.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 56 - 0
third/drupal/merbond/docker-compose.yml

@@ -0,0 +1,56 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --https 8007 http://127.0.0.1:8007
+# sudo tailscale serve --https=8007 off
+# sudo tailscale serve status
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-merbond
+    hostname: merbond
+    environment:
+      - TS_AUTHKEY=tskey-auth-kwiXvkEsFM11CNTRL-Xd4ueBn38wWdCzVWJx5AwWUwpzzDn9g3
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/merbond.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: registry.odamus.com/drupal/drupal_7_rong:latest
+    container_name: drupal_merbond
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    #ports:
+    #  - "127.0.0.1:8007:80"
+    volumes:
+      - html:/var/www/html
+      - backups:/root/drush-backups
+      - /backups/docker/drupal/merbond:/backups
+      - /etc/localtime:/etc/localtime
+    #networks:
+    #  - ai_network
+
+volumes:
+  html:
+    name: 'drupal_merbond-html'
+    driver: local
+  backups:
+    name: 'drupal_merbond-backups'
+    driver: local
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 6 - 0
third/drupal/merbond/run.sh

@@ -0,0 +1,6 @@
+#!/bin/bash
+
+docker-compose up -d
+
+exit 0
+

+ 59 - 0
third/drupal/mustikas/LOEMIND.md

@@ -0,0 +1,59 @@
+# Drupal mustikas – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/drupal/mustikas/`
+
+Drupal 7 veebisait.
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| ts-mustikas | tailscale/tailscale | – | Tailscale ühendus |
+| drupal_mustikas | registry.odamus.com/drupal/drupal_7_rong | 8008 | Drupal veebisait |
+
+## Docker käsud
+
+```bash
+# Käivita
+docker-compose -f /opt/docker-compose/third/drupal/mustikas/docker-compose.yml up -d
+
+# Peata
+docker-compose -f /opt/docker-compose/third/drupal/mustikas/docker-compose.yml down
+
+# Taaskäivita
+docker-compose -f /opt/docker-compose/third/drupal/mustikas/docker-compose.yml restart
+
+# Logid
+docker-compose -f /opt/docker-compose/third/drupal/mustikas/docker-compose.yml logs -f
+
+# Logid (üks)
+docker-compose -f /opt/docker-compose/third/drupal/mustikas/docker-compose.yml logs -f drupal
+```
+
+## Üksikud konteinerid
+
+```bash
+docker logs drupal_mustikas
+docker logs ts-mustikas
+docker restart drupal_mustikas
+```
+
+## Ligipääs
+
+Drupal on ligipääsetav Tailscale kaudu:
+```bash
+sudo tailscale serve --bg --https 8008 http://127.0.0.1:8008
+```
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/opt/docker-compose/third/drupal/mustikas/state` | Tailscale olek |
+| `/opt/docker-compose/third/drupal/mustikas/config` | Tailscale seadistus |
+| `/backups/docker/drupal/mustikas` | Varukoopiad |
+
+## Võrguinfo
+
+- Drupal kasutab `network_mode: service:ts-network` (Tailscale kaudu)
+- Kohandatud image: `registry.odamus.com/drupal/drupal_7_rong`

+ 39 - 0
third/drupal/mustikas/LOEMIND.txt

@@ -0,0 +1,39 @@
+## ----------- teiste domeeni hoidjate alamdomeenidele sertifikaatide genereerimine -----------
+# Dynamic configuration
+# Ardo
+
+#tls:
+#  certificates:
+#    - certFile: /letsencrypt/owngenerated/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.cer 
+#      keyFile: /letsencrypt/owngenerated/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.key 
+
+
+#### !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+## See töötab
+## Vaata abiks:   https://github.com/acmesh-official/acme.sh
+## Loo saidi juurkataloogi alamkataloogid
+#!/bin/bash
+   mkdir -p /var/lib/docker/volumes/drupal_mustikas-1-html/_data/.well-known/acme-challenge
+   cd /root/.acme.sh
+   acme.sh --issue -d mustikas.maastikuarhitekt.ee -w /var/lib/docker/volumes/drupal_mustikas-1-html/_data
+   cp -R /root/.acme.sh/mustikas.maastikuarhitekt.ee/* /var/lib/docker/volumes/traefik_certs/_data/owngenerated/mustikas.maastikuarhitekt.ee/
+#   taaskäivita traefik ja vaata, et see fail on kah õiges kohas.
+   docker service update traefik_traefik
+## Sertifikaatide värskendamine
+#  toimub automaatselt iga 60 päeva järele. 
+
+## ===================== moodulite värskendamine ========================
+docker exec -ti drupal_mustikas.1.  bash
+## prepopulate mooduli mitte-uuendamine
+drush pm-updatecode --lock=prepopulate
+# drupali tuuma uuendamine
+drush up drupal
+# andmebaasi uuendamine
+drush updb
+# clear cache
+drush cc all
+# registry rebuild
+drush rr
+# moodulite uuendamine
+drush up
+

+ 1 - 0
third/drupal/mustikas/account.conf

@@ -0,0 +1 @@
+USER_PATH='/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin'

+ 2 - 0
third/drupal/mustikas/ca/acme-v02.api.letsencrypt.org/ca.conf

@@ -0,0 +1,2 @@
+ACCOUNT_URL='https://acme-v02.api.letsencrypt.org/acme/acct/110071310'
+CA_KEY_HASH='1jZGQAwud61KqXCC6YUyRZzFZMS7vuhUXQF3SCb5EEY='

+ 7 - 0
third/drupal/mustikas/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 19 - 0
third/drupal/mustikas/config/mustikas.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 58 - 0
third/drupal/mustikas/docker-compose.yml

@@ -0,0 +1,58 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --https 8008 http://127.0.0.1:8008
+# sudo tailscale serve --https=8008 off
+# sudo tailscale serve status
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-mustikas
+    hostname: mustikas
+    environment:
+      - TS_AUTHKEY=tskey-auth-kRL2zfvzRs11CNTRL-LGBy2N3nDNDU2d5ot7jBNDLBw54FsrK8U
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/mustikas.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+      - LANG=C.UTF-8
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: registry.odamus.com/drupal/drupal_7_rong:latest
+    container_name: drupal_mustikas
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    #ports:
+    #  - "127.0.0.1:8008:80"
+    volumes:
+      - html:/var/www/html
+      - backups:/root/drush-backups
+      - /backups/docker/drupal/mustikas:/backups
+      - /etc/localtime:/etc/localtime
+    #networks:
+    #  - ai_network
+    restart: unless-stopped
+
+volumes:
+  html:
+    name: 'drupal_mustikas-html'
+    driver: local
+  backups:
+    name: 'drupal_mustikas-backups'
+    driver: local
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 12 - 0
third/drupal/mustikas/http.header

@@ -0,0 +1,12 @@
+HTTP/2 200 
+server: nginx
+date: Tue, 19 Jan 2021 19:11:40 GMT
+content-type: application/pem-certificate-chain
+content-length: 3466
+cache-control: public, max-age=0, no-cache
+link: <https://acme-v02.api.letsencrypt.org/directory>;rel="index"
+link: <https://acme-v02.api.letsencrypt.org/acme/cert/040c025aa3dedc62bc5ce5aa72adbd1b932f/1>;rel="alternate"
+replay-nonce: 0004M_xMFCgDpqH-kLs-fsa_A-PGTTb7wv287p-uDwyFP8o
+x-frame-options: DENY
+strict-transport-security: max-age=604800
+

+ 27 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/ca.cer

@@ -0,0 +1,27 @@
+
+-----BEGIN CERTIFICATE-----
+MIIEZTCCA02gAwIBAgIQQAF1BIMUpMghjISpDBbN3zANBgkqhkiG9w0BAQsFADA/
+MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
+DkRTVCBSb290IENBIFgzMB4XDTIwMTAwNzE5MjE0MFoXDTIxMDkyOTE5MjE0MFow
+MjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUxldCdzIEVuY3J5cHQxCzAJBgNVBAMT
+AlIzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuwIVKMz2oJTTDxLs
+jVWSw/iC8ZmmekKIp10mqrUrucVMsa+Oa/l1yKPXD0eUFFU1V4yeqKI5GfWCPEKp
+Tm71O8Mu243AsFzzWTjn7c9p8FoLG77AlCQlh/o3cbMT5xys4Zvv2+Q7RVJFlqnB
+U840yFLuta7tj95gcOKlVKu2bQ6XpUA0ayvTvGbrZjR8+muLj1cpmfgwF126cm/7
+gcWt0oZYPRfH5wm78Sv3htzB2nFd1EbjzK0lwYi8YGd1ZrPxGPeiXOZT/zqItkel
+/xMY6pgJdz+dU/nPAeX1pnAXFK9jpP+Zs5Od3FOnBv5IhR2haa4ldbsTzFID9e1R
+oYvbFQIDAQABo4IBaDCCAWQwEgYDVR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8E
+BAMCAYYwSwYIKwYBBQUHAQEEPzA9MDsGCCsGAQUFBzAChi9odHRwOi8vYXBwcy5p
+ZGVudHJ1c3QuY29tL3Jvb3RzL2RzdHJvb3RjYXgzLnA3YzAfBgNVHSMEGDAWgBTE
+p7Gkeyxx+tvhS5B1/8QVYIWJEDBUBgNVHSAETTBLMAgGBmeBDAECATA/BgsrBgEE
+AYLfEwEBATAwMC4GCCsGAQUFBwIBFiJodHRwOi8vY3BzLnJvb3QteDEubGV0c2Vu
+Y3J5cHQub3JnMDwGA1UdHwQ1MDMwMaAvoC2GK2h0dHA6Ly9jcmwuaWRlbnRydXN0
+LmNvbS9EU1RST09UQ0FYM0NSTC5jcmwwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYf
+r52LFMLGMB0GA1UdJQQWMBQGCCsGAQUFBwMBBggrBgEFBQcDAjANBgkqhkiG9w0B
+AQsFAAOCAQEA2UzgyfWEiDcx27sT4rP8i2tiEmxYt0l+PAK3qB8oYevO4C5z70kH
+ejWEHx2taPDY/laBL21/WKZuNTYQHHPD5b1tXgHXbnL7KqC401dk5VvCadTQsvd8
+S8MXjohyc9z9/G2948kLjmE6Flh9dDYrVYA9x2O+hEPGOaEOa1eePynBgPayvUfL
+qjBstzLhWVQLGAkXXmNs+5ZnPBxzDJOLxhF2JIbeQAcH5H0tZrUlo5ZYyOqA7s9p
+O5b85o3AM/OJ+CktFBQtfvBhcJVd9wvlwPsk+uyOy2HI7mNxKKgsBTt375teA2Tw
+UdHkhVNcsAKX1H7GNNLOEADksd86wuoXvg==
+-----END CERTIFICATE-----

+ 58 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/fullchain.cer

@@ -0,0 +1,58 @@
+-----BEGIN CERTIFICATE-----
+MIIFPjCCBCagAwIBAgISBAwCWqPe3GK8XOWqcq29G5MvMA0GCSqGSIb3DQEBCwUA
+MDIxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MQswCQYDVQQD
+EwJSMzAeFw0yMTAxMTkxODExMzlaFw0yMTA0MTkxODExMzlaMCcxJTAjBgNVBAMT
+HG11c3Rpa2FzLm1hYXN0aWt1YXJoaXRla3QuZWUwggEiMA0GCSqGSIb3DQEBAQUA
+A4IBDwAwggEKAoIBAQC/XSg9MLP1hZ4KXFdy7OmaUPXmdIiB4gD5hJ1Y/cQt5RhK
+SDJJDdn4tcA0UAiZShBX+CVk0+PFP3W5TTBQZTDqNuhDwbMqUD6XSnsL7J5pe9O5
+ldzPe04k+ox0ozCtEDe3EYIy+b5dIEOyL5evN//RwlmEKQkL6ldRJtqVyWa8EXN1
+i8OasSqUFqhlF/g24FGWX9N9e5cFSXcGSDKVL8dUk4ttk8MAfhUCNZxPXRIRFdGy
+mJCaCwmKXtvoUqOFOQI7ACgJDXGVpBA5znhmdsKTZUEQS5nARi93UYRZFzu031NW
++giYBFB9541yd2bictvty1hY87paAugYKq8wx+L3AgMBAAGjggJXMIICUzAOBgNV
+HQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMAwGA1Ud
+EwEB/wQCMAAwHQYDVR0OBBYEFAVjzs4yKxq6lPZwsRDY9oEWy6SfMB8GA1UdIwQY
+MBaAFBQusxe3WFbLrlAJQOYfr52LFMLGMFUGCCsGAQUFBwEBBEkwRzAhBggrBgEF
+BQcwAYYVaHR0cDovL3IzLm8ubGVuY3Iub3JnMCIGCCsGAQUFBzAChhZodHRwOi8v
+cjMuaS5sZW5jci5vcmcvMCcGA1UdEQQgMB6CHG11c3Rpa2FzLm1hYXN0aWt1YXJo
+aXRla3QuZWUwTAYDVR0gBEUwQzAIBgZngQwBAgEwNwYLKwYBBAGC3xMBAQEwKDAm
+BggrBgEFBQcCARYaaHR0cDovL2Nwcy5sZXRzZW5jcnlwdC5vcmcwggEEBgorBgEE
+AdZ5AgQCBIH1BIHyAPAAdgBvU3asMfAxGdiZAKRRFf93FRwR2QLBACkGjbIImjfZ
+EwAAAXccD0eYAAAEAwBHMEUCIC18jJ/GGt3LXePTKZHWXyxwIG4V/ODR/7HYyxbF
+LH2CAiEAl+8aWtEo+a6hLGRz0ABRrgCqH/0NTC5CrdR5hN1y1T4AdgD2XJQv0Xcw
+IhRUGAgwlFaO400TGTO/3wwvIAvMTvFk4wAAAXccD0fnAAAEAwBHMEUCIDOjMmKk
+P9o3LCoIueFflOABAZCC/svBKwHyTfXAfMQ2AiEA+ZitIPUOMlRCPMEIh/t+PKNe
+ebhVrAfcB5oribSW4uAwDQYJKoZIhvcNAQELBQADggEBAB+WBv6YCUkC9ehOW96g
+gZva4R1l1l2COLPYkDI1ONAt1kQobxqoUPDFx252G2TF/WKUaEc2DBCB0814+AJo
+4RTe1y2RVtkOldYlh97yLnGOzB/kQA/OLfasF9c91UOiGdOtJ6O+PPCPZ39F4qxO
+c6k0b1eXJrm6EQPKsrk5nV0etAVClxfQqQVWitZX146zVY2NjYZPJuxGAtedG/Bn
+xd3pHjusxtjPudeDEi/YYCkUy/82hfjzVOQSi6/NyQgAcZ5gYso+tPbkQPPiEvQr
+JIKAnbLu/xnSeQPLxq/irnlSRcQ351d6CEk6ZpFpSUfpNrKUhUduu5d55y9AY5Zc
+kRM=
+-----END CERTIFICATE-----
+
+-----BEGIN CERTIFICATE-----
+MIIEZTCCA02gAwIBAgIQQAF1BIMUpMghjISpDBbN3zANBgkqhkiG9w0BAQsFADA/
+MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
+DkRTVCBSb290IENBIFgzMB4XDTIwMTAwNzE5MjE0MFoXDTIxMDkyOTE5MjE0MFow
+MjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUxldCdzIEVuY3J5cHQxCzAJBgNVBAMT
+AlIzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuwIVKMz2oJTTDxLs
+jVWSw/iC8ZmmekKIp10mqrUrucVMsa+Oa/l1yKPXD0eUFFU1V4yeqKI5GfWCPEKp
+Tm71O8Mu243AsFzzWTjn7c9p8FoLG77AlCQlh/o3cbMT5xys4Zvv2+Q7RVJFlqnB
+U840yFLuta7tj95gcOKlVKu2bQ6XpUA0ayvTvGbrZjR8+muLj1cpmfgwF126cm/7
+gcWt0oZYPRfH5wm78Sv3htzB2nFd1EbjzK0lwYi8YGd1ZrPxGPeiXOZT/zqItkel
+/xMY6pgJdz+dU/nPAeX1pnAXFK9jpP+Zs5Od3FOnBv5IhR2haa4ldbsTzFID9e1R
+oYvbFQIDAQABo4IBaDCCAWQwEgYDVR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8E
+BAMCAYYwSwYIKwYBBQUHAQEEPzA9MDsGCCsGAQUFBzAChi9odHRwOi8vYXBwcy5p
+ZGVudHJ1c3QuY29tL3Jvb3RzL2RzdHJvb3RjYXgzLnA3YzAfBgNVHSMEGDAWgBTE
+p7Gkeyxx+tvhS5B1/8QVYIWJEDBUBgNVHSAETTBLMAgGBmeBDAECATA/BgsrBgEE
+AYLfEwEBATAwMC4GCCsGAQUFBwIBFiJodHRwOi8vY3BzLnJvb3QteDEubGV0c2Vu
+Y3J5cHQub3JnMDwGA1UdHwQ1MDMwMaAvoC2GK2h0dHA6Ly9jcmwuaWRlbnRydXN0
+LmNvbS9EU1RST09UQ0FYM0NSTC5jcmwwHQYDVR0OBBYEFBQusxe3WFbLrlAJQOYf
+r52LFMLGMB0GA1UdJQQWMBQGCCsGAQUFBwMBBggrBgEFBQcDAjANBgkqhkiG9w0B
+AQsFAAOCAQEA2UzgyfWEiDcx27sT4rP8i2tiEmxYt0l+PAK3qB8oYevO4C5z70kH
+ejWEHx2taPDY/laBL21/WKZuNTYQHHPD5b1tXgHXbnL7KqC401dk5VvCadTQsvd8
+S8MXjohyc9z9/G2948kLjmE6Flh9dDYrVYA9x2O+hEPGOaEOa1eePynBgPayvUfL
+qjBstzLhWVQLGAkXXmNs+5ZnPBxzDJOLxhF2JIbeQAcH5H0tZrUlo5ZYyOqA7s9p
+O5b85o3AM/OJ+CktFBQtfvBhcJVd9wvlwPsk+uyOy2HI7mNxKKgsBTt375teA2Tw
+UdHkhVNcsAKX1H7GNNLOEADksd86wuoXvg==
+-----END CERTIFICATE-----

+ 31 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.cer

@@ -0,0 +1,31 @@
+-----BEGIN CERTIFICATE-----
+MIIFPjCCBCagAwIBAgISBAwCWqPe3GK8XOWqcq29G5MvMA0GCSqGSIb3DQEBCwUA
+MDIxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MQswCQYDVQQD
+EwJSMzAeFw0yMTAxMTkxODExMzlaFw0yMTA0MTkxODExMzlaMCcxJTAjBgNVBAMT
+HG11c3Rpa2FzLm1hYXN0aWt1YXJoaXRla3QuZWUwggEiMA0GCSqGSIb3DQEBAQUA
+A4IBDwAwggEKAoIBAQC/XSg9MLP1hZ4KXFdy7OmaUPXmdIiB4gD5hJ1Y/cQt5RhK
+SDJJDdn4tcA0UAiZShBX+CVk0+PFP3W5TTBQZTDqNuhDwbMqUD6XSnsL7J5pe9O5
+ldzPe04k+ox0ozCtEDe3EYIy+b5dIEOyL5evN//RwlmEKQkL6ldRJtqVyWa8EXN1
+i8OasSqUFqhlF/g24FGWX9N9e5cFSXcGSDKVL8dUk4ttk8MAfhUCNZxPXRIRFdGy
+mJCaCwmKXtvoUqOFOQI7ACgJDXGVpBA5znhmdsKTZUEQS5nARi93UYRZFzu031NW
++giYBFB9541yd2bictvty1hY87paAugYKq8wx+L3AgMBAAGjggJXMIICUzAOBgNV
+HQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMAwGA1Ud
+EwEB/wQCMAAwHQYDVR0OBBYEFAVjzs4yKxq6lPZwsRDY9oEWy6SfMB8GA1UdIwQY
+MBaAFBQusxe3WFbLrlAJQOYfr52LFMLGMFUGCCsGAQUFBwEBBEkwRzAhBggrBgEF
+BQcwAYYVaHR0cDovL3IzLm8ubGVuY3Iub3JnMCIGCCsGAQUFBzAChhZodHRwOi8v
+cjMuaS5sZW5jci5vcmcvMCcGA1UdEQQgMB6CHG11c3Rpa2FzLm1hYXN0aWt1YXJo
+aXRla3QuZWUwTAYDVR0gBEUwQzAIBgZngQwBAgEwNwYLKwYBBAGC3xMBAQEwKDAm
+BggrBgEFBQcCARYaaHR0cDovL2Nwcy5sZXRzZW5jcnlwdC5vcmcwggEEBgorBgEE
+AdZ5AgQCBIH1BIHyAPAAdgBvU3asMfAxGdiZAKRRFf93FRwR2QLBACkGjbIImjfZ
+EwAAAXccD0eYAAAEAwBHMEUCIC18jJ/GGt3LXePTKZHWXyxwIG4V/ODR/7HYyxbF
+LH2CAiEAl+8aWtEo+a6hLGRz0ABRrgCqH/0NTC5CrdR5hN1y1T4AdgD2XJQv0Xcw
+IhRUGAgwlFaO400TGTO/3wwvIAvMTvFk4wAAAXccD0fnAAAEAwBHMEUCIDOjMmKk
+P9o3LCoIueFflOABAZCC/svBKwHyTfXAfMQ2AiEA+ZitIPUOMlRCPMEIh/t+PKNe
+ebhVrAfcB5oribSW4uAwDQYJKoZIhvcNAQELBQADggEBAB+WBv6YCUkC9ehOW96g
+gZva4R1l1l2COLPYkDI1ONAt1kQobxqoUPDFx252G2TF/WKUaEc2DBCB0814+AJo
+4RTe1y2RVtkOldYlh97yLnGOzB/kQA/OLfasF9c91UOiGdOtJ6O+PPCPZ39F4qxO
+c6k0b1eXJrm6EQPKsrk5nV0etAVClxfQqQVWitZX146zVY2NjYZPJuxGAtedG/Bn
+xd3pHjusxtjPudeDEi/YYCkUy/82hfjzVOQSi6/NyQgAcZ5gYso+tPbkQPPiEvQr
+JIKAnbLu/xnSeQPLxq/irnlSRcQ351d6CEk6ZpFpSUfpNrKUhUduu5d55y9AY5Zc
+kRM=
+-----END CERTIFICATE-----

+ 15 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.conf

@@ -0,0 +1,15 @@
+Le_Domain='mustikas.maastikuarhitekt.ee'
+Le_Alt='no'
+Le_Webroot='/var/lib/docker/volumes/drupal_mustikas-1-html/_data'
+Le_PreHook=''
+Le_PostHook=''
+Le_RenewHook=''
+Le_API='https://acme-v02.api.letsencrypt.org/directory'
+Le_Keylength=''
+Le_OrderFinalize='https://acme-v02.api.letsencrypt.org/acme/finalize/110071310/7407443351'
+Le_LinkOrder='https://acme-v02.api.letsencrypt.org/acme/order/110071310/7407443351'
+Le_LinkCert='https://acme-v02.api.letsencrypt.org/acme/cert/040c025aa3dedc62bc5ce5aa72adbd1b932f'
+Le_CertCreateTime='1611083500'
+Le_CertCreateTimeStr='Tue Jan 19 19:11:40 UTC 2021'
+Le_NextRenewTimeStr='Sat Mar 20 19:11:40 UTC 2021'
+Le_NextRenewTime='1616181100'

+ 17 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.csr

@@ -0,0 +1,17 @@
+-----BEGIN CERTIFICATE REQUEST-----
+MIICszCCAZsCAQAwJzElMCMGA1UEAwwcbXVzdGlrYXMubWFhc3Rpa3VhcmhpdGVr
+dC5lZTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAL9dKD0ws/WFngpc
+V3Ls6ZpQ9eZ0iIHiAPmEnVj9xC3lGEpIMkkN2fi1wDRQCJlKEFf4JWTT48U/dblN
+MFBlMOo26EPBsypQPpdKewvsnml707mV3M97TiT6jHSjMK0QN7cRgjL5vl0gQ7Iv
+l683/9HCWYQpCQvqV1Em2pXJZrwRc3WLw5qxKpQWqGUX+DbgUZZf0317lwVJdwZI
+MpUvx1STi22TwwB+FQI1nE9dEhEV0bKYkJoLCYpe2+hSo4U5AjsAKAkNcZWkEDnO
+eGZ2wpNlQRBLmcBGL3dRhFkXO7TfU1b6CJgEUH3njXJ3ZuJy2+3LWFjzuloC6Bgq
+rzDH4vcCAwEAAaBHMEUGCSqGSIb3DQEJDjE4MDYwCwYDVR0PBAQDAgXgMCcGA1Ud
+EQQgMB6CHG11c3Rpa2FzLm1hYXN0aWt1YXJoaXRla3QuZWUwDQYJKoZIhvcNAQEL
+BQADggEBADSEcxyk7pPNry7+PKW7mvVH82DGUGLKEi1C7F44IAgYE2j6uV79GG+/
+00lrolsow7OZ/xgN/QCmU197CR/OCkWYzud0stbZkU0/x64EOctqA8WdIPxyHFL0
+g85QaQDLA7nIXPfUrx8zcGhOPqWhDCHZWPKOZThRyMIiLhbVdfPkUiqkzv4EZb32
+m8Qe09Ca+pe/DRfQbd9zIu86SJbkYT4jaXqj9S3SKCWkqRoZB6EWDUowvgtIhBED
+SsziReqApaj31ekl1XeLKeXPglOR3U56EqXf+7QZAaQX6FWWL/mmT4i0Hjt6bFrz
+kWVWf4LIjhxrguJfD8Coxv2mV7oACkA=
+-----END CERTIFICATE REQUEST-----

+ 8 - 0
third/drupal/mustikas/mustikas.maastikuarhitekt.ee/mustikas.maastikuarhitekt.ee.csr.conf

@@ -0,0 +1,8 @@
+[ req_distinguished_name ]
+[ req ]
+distinguished_name = req_distinguished_name
+req_extensions = v3_req
+[ v3_req ]
+
+keyUsage = nonRepudiation, digitalSignature, keyEncipherment
+subjectAltName=DNS:mustikas.maastikuarhitekt.ee

+ 6 - 0
third/drupal/mustikas/run.sh

@@ -0,0 +1,6 @@
+#!/bin/bash
+
+docker-compose up -d
+
+exit 0
+

+ 25 - 0
third/drupal/mustikas/sertifikaatide_genereerimine.sh

@@ -0,0 +1,25 @@
+#!/bin/bash
+
+# acme.sh abil TLS sertifkaatide genereerimine ja paigutamine õigesse kohta.
+# Selleks peab html konteiner jooksma aadressil http://ldap.odamus.com/.well-known
+##
+## Acme peaks ise genereerima sertifikaadi. Lisa cron'i, et iga kuu kopeeritakse
+## sertifikaadid õigesse kohta ja taaskäivitatakse dockeri service.
+## Sertifikaatide värskendamine
+##  toimub automaatselt iga 60 päeva järele.
+
+
+
+
+## Vaata abiks:   https://github.com/acmesh-official/acme.sh
+mkdir -p /var/lib/docker/volumes/drupal_mustikas-1-html/_data/.well-known/acme-challenge
+cd /root/.acme.sh
+
+  ./acme.sh --issue -d mustikas.maastikuarhitekt.ee -w /var/lib/docker/volumes/drupal_mustikas-1-html/_data --home /var/lib/docker/volumes/traefik_certs/_data/owngenerated
+
+
+##   taaskäivita traefik ja vaata, et see fail on kah õiges kohas.
+cd /opt/containers/server/traefik
+ ./cleanup.sh && ./run.sh
+#   docker service update traefik_traefik
+cd /opt/containers/cms/drupal/mustikas

+ 39 - 0
third/drupal/mustikas/sync_from_hetzner.sh

@@ -0,0 +1,39 @@
+#!/usr/bin/env bash
+# =============================================================================
+# Hetzner -> ohmu: dr_mustikas andmebaasi + Drupali HTML sünkroonimine
+# Välja arvatud settings.php (ohmu oma jääb alles)
+# Käivita root õigustega: sudo bash sync_from_hetzner.sh
+# =============================================================================
+set -e
+
+HETZNER="root@100.80.222.54"
+OHMU_MARIADB_PASS="ai_root_pass_2026"
+HETZNER_HTML="/var/lib/docker/volumes/drupal_mustikas-1-html/_data"
+OHMU_HTML="/var/lib/docker/volumes/drupal_mustikas-html/_data"
+
+echo "=== $(date): Alustan sünkroonimist ==="
+
+# 1. MariaDB: dump hetznerist ja import ohmu-sse
+echo "[1/3] MariaDB: dump hetzner dr_mustikas -> ohmu mariadb ..."
+ssh "$HETZNER" "docker exec mariadb_simple sh -c 'mariadb-dump -u root -p\"\$(cat /run/secrets/mysql_root_password)\" --single-transaction dr_mustikas'" \
+  | docker exec -i mariadb mariadb -u root -p"$OHMU_MARIADB_PASS" dr_mustikas 2>/dev/null
+echo "  DB sünkroonitud."
+
+# 2. Rsync Drupali HTML (v.a settings.php) — vajab root õigusi
+echo "[2/3] Rsync: hetzner HTML -> ohmu (v.a settings.php) ..."
+rsync -av --delete --exclude="settings.php" -e "ssh" \
+  "$HETZNER:$HETZNER_HTML/" \
+  "$OHMU_HTML/"
+echo "  HTML sünkroonitud."
+
+# 3. Tühjenda Drupali puhver
+echo "[3/3] Drupali puhvri tühjendamine..."
+docker exec drupal_mustikas sh -c "cd /var/www/html && php -r '
+  include_once \"includes/bootstrap.inc\";
+  drupal_bootstrap(DRUPAL_BOOTSTRAP_FULL);
+  cache_clear_all();
+  drupal_set_message(\"Cache cleared.\");
+'" 2>/dev/null || docker exec drupal_mustikas sh -c "rm -rf /var/www/html/sites/default/files/cache/*" 2>/dev/null || echo "  (puhvri tühjendamine jäi vahele)"
+
+echo ""
+echo "=== $(date): Sünkroonimine valmis ==="

+ 59 - 0
third/drupal/see1/LOEMIND.md

@@ -0,0 +1,59 @@
+# Drupal see1 – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/drupal/see1/`
+
+Drupal 9 veebisait.
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| ts-see1 | tailscale/tailscale | – | Tailscale ühendus |
+| drupal_see1 | drupal:9 | 8005 | Drupal veebisait |
+
+## Docker käsud
+
+```bash
+# Käivita
+docker-compose -f /opt/docker-compose/third/drupal/see1/docker-compose.yml up -d
+
+# Peata
+docker-compose -f /opt/docker-compose/third/drupal/see1/docker-compose.yml down
+
+# Taaskäivita
+docker-compose -f /opt/docker-compose/third/drupal/see1/docker-compose.yml restart
+
+# Logid
+docker-compose -f /opt/docker-compose/third/drupal/see1/docker-compose.yml logs -f
+
+# Logid (üks)
+docker-compose -f /opt/docker-compose/third/drupal/see1/docker-compose.yml logs -f drupal
+```
+
+## Üksikud konteinerid
+
+```bash
+docker logs drupal_see1
+docker logs ts-see1
+docker restart drupal_see1
+```
+
+## Ligipääs
+
+Drupal on ligipääsetav Tailscale kaudu:
+```bash
+sudo tailscale serve --bg --https 8005 http://127.0.0.1:8005
+```
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/opt/docker-compose/third/drupal/see1/state` | Tailscale olek |
+| `/opt/docker-compose/third/drupal/see1/config` | Tailscale seadistus |
+| `/backups/docker/drupal/see1` | Varukoopiad |
+
+## Võrguinfo
+
+- Drupal kasutab `network_mode: service:ts-network` (Tailscale kaudu)
+- Andmebaas on tõenäoliselt eraldi (väljaspool seda compose'i)

+ 23 - 0
third/drupal/see1/LOEMIND.txt

@@ -0,0 +1,23 @@
+
+apt update
+apt -y install curl git unzip vim wget && \
+apt-get clean
+# Drupali tuuma install
+composer install
+# To see which versions of Drupal core are available, use this command
+composer show drupal/recommended-project --all
+#Check for available Drupal core and module updates:
+composer outdated drupal/*
+# All of your modules and themes can be updated along with Drupal core via:
+composer update
+
+
+# Mooduli install
+php -d memory_limit=-1 `which composer` require 'drupal/masquerade' --update-no-dev  --update-with-all-dependencies
+# SMTP
+php -d memory_limit=-1 `which composer` require 'phpmailer/phpmailer' --update-no-dev
+php -d memory_limit=-1 `which composer` require 'drupal/smtp' --update-no-dev --update-with-all-dependencies
+# Theme
+php -d memory_limit=-1 `which composer` require 'drupal/d8w3css' --update-no-dev --update-with-all-dependencies
+#composer remove 'drupal/d8w3css' --update-with-dependencies
+

+ 7 - 0
third/drupal/see1/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 19 - 0
third/drupal/see1/config/see1.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 63 - 0
third/drupal/see1/docker-compose.yml

@@ -0,0 +1,63 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --https 8005 http://127.0.0.1:8005
+# sudo tailscale serve --https=8005 off
+# sudo tailscale serve status
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-see1
+    hostname: see1
+    environment:
+      - TS_AUTHKEY=tskey-auth-k8tw1o22ag11CNTRL-CVRECjx9BcE2zzsxq4VDcET1KzxcbiaAA
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/see1.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+      - LANG=C.UTF-8
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: drupal:9
+    container_name: drupal_see1
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    volumes:
+      - modules:/opt/drupal/web/modules
+      - profile:/opt/drupal/web/profiles
+      - theme:/opt/drupal/web/themes
+      - sites:/opt/drupal/web/sites
+      - /backups/docker/drupal/see1:/backups
+      - /etc/localtime:/etc/localtime
+#    networks:
+#      - ai_network
+    restart: unless-stopped
+
+volumes:
+  modules:
+    name: 'drupal_see1-modules'
+    driver: local
+  profile:
+    name: 'drupal_see1-profile'
+    driver: local
+  theme:
+    name: 'drupal_see1-theme'
+    driver: local
+  sites:
+    name: 'drupal_see1-sites'
+    driver: local
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 11 - 0
third/drupal/see1/run.sh

@@ -0,0 +1,11 @@
+#!/bin/bash
+
+docker-compose up -d
+sleep 10
+docker exec -it $(docker ps -f name=drupal_see1 -q) bash -c "apt update; \
+apt -y install curl git unzip vim wget; \
+apt-get clean; 
+"
+
+exit 0
+

+ 23 - 0
third/drupal/terminator/LOEMIND.txt

@@ -0,0 +1,23 @@
+
+apt update
+apt -y install curl git unzip vim wget && \
+apt-get clean
+# Drupali tuuma install
+composer install
+# To see which versions of Drupal core are available, use this command
+composer show drupal/recommended-project --all
+#Check for available Drupal core and module updates:
+composer outdated drupal/*
+# All of your modules and themes can be updated along with Drupal core via:
+composer update
+
+
+# Mooduli install
+php -d memory_limit=-1 `which composer` require 'drupal/masquerade' --update-no-dev  --update-with-all-dependencies
+# SMTP
+php -d memory_limit=-1 `which composer` require 'phpmailer/phpmailer' --update-no-dev
+php -d memory_limit=-1 `which composer` require 'drupal/smtp' --update-no-dev --update-with-all-dependencies
+# Theme
+php -d memory_limit=-1 `which composer` require 'drupal/d8w3css' --update-no-dev --update-with-all-dependencies
+#composer remove 'drupal/d8w3css' --update-with-dependencies
+

+ 7 - 0
third/drupal/terminator/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 19 - 0
third/drupal/terminator/config/terminator.json

@@ -0,0 +1,19 @@
+{
+    "TCP": {
+      "443": {
+        "HTTPS": true
+      }
+    },
+    "Web": {
+      "${TS_CERT_DOMAIN}:443": {
+        "Handlers": {
+          "/": {
+            "Proxy": "http://127.0.0.1:80"
+          }
+        }
+      }
+    },
+    "AllowFunnel": {
+      "${TS_CERT_DOMAIN}:443": false
+    }
+  }

+ 65 - 0
third/drupal/terminator/docker-compose.yml

@@ -0,0 +1,65 @@
+version: "3.9"
+# Tailscale ühendus:
+# sudo tailscale serve --bg --https 8006 http://127.0.0.1:8006
+# sudo tailscale serve --https=8006 off
+# sudo tailscale serve status
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-terminator
+    hostname: terminator
+    environment:
+      - TS_AUTHKEY=tskey-auth-kR6hE3ikuX11CNTRL-Hz9qFdBt5u41zaPCd6y7u4yMrhUb8vRh
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/terminator.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+    volumes:
+      - ${PWD}/state:/var/lib/tailscale
+      - ${PWD}/config:/config
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  drupal:
+    image: drupal:8-apache
+    container_name: drupal_terminator
+    network_mode: service:ts-network
+    depends_on:
+      - ts-network
+    #ports:
+    #  - "127.0.0.1:8006:80"
+    volumes:
+      - modules:/opt/drupal/web/modules
+      - profile:/opt/drupal/web/profiles
+      - theme:/opt/drupal/web/themes
+      - sites:/opt/drupal/web/sites
+      - /backups/docker/drupal/terminator:/backups
+      - /etc/localtime:/etc/localtime
+    #networks:
+    #  - ai_network
+    restart: unless-stopped
+
+volumes:
+  modules:
+    name: 'drupal_terminator-modules'
+    driver: local
+  profile:
+    name: 'drupal_terminator-profile'
+    driver: local
+  theme:
+    name: 'drupal_terminator-theme'
+    driver: local
+  sites:
+    name: 'drupal_terminator-sites'
+    driver: local
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 9 - 0
third/drupal/terminator/run.sh

@@ -0,0 +1,9 @@
+#!/bin/bash
+
+docker-compose up -d
+sleep 10
+#docker exec -it $(docker ps -f name=drupal_terminator -q) bash -c "composer require phpmailer/phpmailer --update-no-dev; \
+#ls"
+
+exit 0
+

+ 17 - 0
third/drupal/terminator/scripts/composer_install.sh

@@ -0,0 +1,17 @@
+#!/bin/sh
+
+EXPECTED_CHECKSUM="$(wget -q -O - https://composer.github.io/installer.sig)"
+php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');"
+ACTUAL_CHECKSUM="$(php -r "echo hash_file('sha384', 'composer-setup.php');")"
+
+if [ "$EXPECTED_CHECKSUM" != "$ACTUAL_CHECKSUM" ]
+then
+    >&2 echo 'ERROR: Invalid installer checksum'
+    rm composer-setup.php
+    exit 1
+fi
+
+php composer-setup.php --quiet
+RESULT=$?
+rm composer-setup.php
+exit $RESULT

+ 102 - 0
third/n8n/LOEMIND.md

@@ -0,0 +1,102 @@
+# n8n – Docker kasutusjuhend
+
+Kataloog: `/opt/docker-compose/third/n8n/`
+
+Töövoogude automatiseerimise platvorm (n8n) + Playwright brauseriserver.
+
+## Teenused
+
+| Konteiner | Pilt | Port | Selgitus |
+|-----------|------|------|----------|
+| ts-n8n | tailscale/tailscale | – | Tailscale ühendus n8n-ile |
+| n8n | n8nio/n8n | 5678 | Töövoogude mootor |
+| n8n-runners | n8n-runner-custom | – | n8n kooditöötlejad |
+| playwright | mcr.microsoft.com/playwright | 3003 | Playwright brauseriserver |
+
+## Docker käsud
+
+```bash
+# Käivita
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml up -d
+
+# Peata
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml down
+
+# Taaskäivita
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml restart n8n
+
+# Logid (kõik)
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml logs -f
+
+# Logid (üks)
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml logs -f n8n
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml logs -f playwright
+
+# Uuenda
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml pull
+docker-compose -f /opt/docker-compose/third/n8n/docker-compose.yml up -d
+```
+
+## Üksikud konteinerid
+
+```bash
+# n8n
+docker logs n8n
+docker restart n8n
+
+# n8n runners
+docker logs n8n-runners
+
+# Playwright server
+docker logs playwright
+curl http://100.87.1.24:3003/json/version
+
+# Sisene n8n konteinerisse
+docker exec -it n8n /bin/sh
+
+# Sisene Playwright konteinerisse
+docker exec -it playwright /bin/bash
+```
+
+## Ligipääs
+
+| Teenus | URL |
+|--------|-----|
+| n8n (Tailscale) | https://n8n.tail20e23.ts.net |
+| Playwright | http://100.87.1.24:3003 |
+
+## n8n veebiliides
+
+n8n on ligipääsetav ainult Tailscale kaudu:
+```bash
+sudo tailscale serve --bg --https 9091 http://127.0.0.1:9091
+```
+
+## Playwright kasutamine
+
+```python
+from playwright.sync_api import sync_playwright
+
+with sync_playwright() as p:
+    browser = p.chromium.connect_over_cdp("http://100.87.1.24:3003")
+    page = browser.new_page()
+    page.goto("https://example.com")
+    print(page.title())
+    browser.close()
+```
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/data/docker/n8n` | n8n andmed ja töövood |
+| `/data/docker/n8n-npm` | npm paketid |
+| `/data/docker/n8n-cache` | Vahemälu |
+| `/data/docker/playwright-browsers` | Playwright brauserid |
+| `/backups/docker/n8n` | Varukoopiad |
+
+## Võrguinfo
+
+- n8n kasutab `network_mode: service:ts-network` (Tailscale kaudu)
+- n8n-runners ja playwright on `ai_network` peal
+- n8n runnerid ühenduvad n8n brokeriga aadressil `n8n:5679`

+ 13 - 0
third/n8n/README.md

@@ -0,0 +1,13 @@
+# n8n
+
+
+
+./cleanup.sh
+nano docker-compose.yml
+# Kontrolli
+docker-compose ps
+# Custom runner
+nano n8n-custom-runner/n8n-task-runners.json 
+# Build
+docker build -t n8n-runner-custom n8n-custom-runner/ && \
+./run.sh

+ 7 - 0
third/n8n/backup_sqlite.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+BACKUP_DIR="/backups/docker/n8n"
+DB_FILE="/data/docker/n8n/database.sqlite"
+TS=$(date +%Y%m%d)
+/usr/bin/sqlite3 "$DB_FILE" ".backup ${BACKUP_DIR}/n8n-database-${TS}.sqlite"
+/usr/bin/gzip -f "${BACKUP_DIR}/n8n-database-${TS}.sqlite"
+/usr/bin/find "$BACKUP_DIR" -name "n8n-database-*.sqlite.gz" -mtime +90 -delete

+ 7 - 0
third/n8n/cleanup.sh

@@ -0,0 +1,7 @@
+#!/bin/bash
+
+echo "Cleaning up..."
+
+docker-compose down
+
+exit 0

+ 16 - 0
third/n8n/config/n8n.json

@@ -0,0 +1,16 @@
+{
+  "TCP": {
+    "443": {
+      "HTTPS": true
+    }
+  },
+  "Web": {
+    "n8n.tail20e23.ts.net:443": {
+      "Handlers": {
+        "/": {
+          "Proxy": "http://n8n:5678"
+        }
+      }
+    }
+  }
+}

+ 109 - 0
third/n8n/docker-compose.yml

@@ -0,0 +1,109 @@
+version: "3.9"
+
+services:
+  ts-network:
+    image: tailscale/tailscale:latest
+    container_name: ts-n8n
+    environment:
+      - TS_AUTHKEY=tskey-auth-kS1DGBXc3H11CNTRL-UuCbbRQBEBBvrQhXreS7BBVwmztVyNSz
+      - "TS_EXTRA_ARGS=--advertise-tags=tag:container --reset"
+      - TS_SERVE_CONFIG=/config/n8n.json
+      - TS_STATE_DIR=/var/lib/tailscale
+      - TS_USERSPACE=false
+      - LANG=C.UTF-8
+    volumes:
+      - /opt/docker-compose/third/n8n/state:/var/lib/tailscale
+      - /opt/docker-compose/third/n8n/config:/config
+      - /etc/localtime:/etc/localtime:ro
+    devices:
+      - /dev/net/tun:/dev/net/tun
+    cap_add:
+      - net_admin
+    restart: unless-stopped
+    networks:
+      - ai_network
+
+  n8n:
+    image: n8nio/n8n:2.27.3
+    container_name: n8n
+    restart: unless-stopped
+    networks:
+      - ai_network
+    ports:
+      - "5678:5678"
+    environment:
+      GENERIC_TIMEZONE: "Europe/Tallinn"
+      N8N_PORT: "5678"
+      N8N_PROTOCOL: "http"
+      N8N_ENCRYPTION_KEY: "d0d68562bfdc68746dab3c4041cda61e96507be3908872ffed3c1a16cb8c47a0"
+      N8N_SECURE_COOKIE: "false"
+      N8N_RUNNERS_MODE: "external"
+      N8N_RUNNERS_AUTH_TOKEN: "super_strong_random_token_change_this_2026"
+      N8N_RUNNERS_BROKER_LISTEN_ADDRESS: "0.0.0.0"
+      N8N_RUNNERS_TASK_TIMEOUT: "300"
+      N8N_RUNNERS_JS_PACKAGES: "playwright"
+      N8N_NATIVE_PYTHON_RUNNER: "true"
+    volumes:
+      - /data/docker/n8n:/home/node/.n8n
+      - /data/docker/n8n-cache:/home/node/.cache
+      - /backups/docker/n8n:/backups
+      - /etc/localtime:/etc/localtime:ro
+
+  n8n-runners:
+    #image: n8nio/runners:latest
+    image: n8n-runner-custom
+    container_name: n8n-runners
+    restart: unless-stopped
+    #user: root
+    environment:
+      - N8N_RUNNERS_TASK_BROKER_URI=http://n8n:5679
+      - N8N_RUNNERS_AUTH_TOKEN=super_strong_random_token_change_this_2026
+      - N8N_RUNNERS_TASK_TIMEOUT=300
+      - NODE_FUNCTION_ALLOW_BUILTIN=*
+      - NODE_FUNCTION_ALLOW_EXTERNAL=ws
+    #extra_hosts:
+    #  - "n8n:100.67.158.94"
+    depends_on:
+      - n8n
+    volumes:
+      - /etc/localtime:/etc/localtime:ro
+      #- ./n8n-task-runners.json:/etc/n8n-task-runners.json:ro
+      #- ./python-venv:/opt/runners/task-runner-python/.venv
+      #- ./n8n-runner-cache:/home/node/.cache/ms-playwright
+      #- /data/docker/n8n-runner-javascript:/opt/runners/task-runner-javascript
+      - /backups/docker/n8n-runners:/backups
+    networks:
+      - ai_network
+
+# ================== PLAYWRIGHT BROWSER SERVER (port 3003) ==================
+  playwright:
+    image: mcr.microsoft.com/playwright:v1.52.0-jammy
+    container_name: playwright
+    restart: unless-stopped
+    user: root
+    environment:
+      - PLAYWRIGHT_BROWSERS_PATH=/ms-playwright
+    volumes:
+      - /data/docker/playwright-browsers:/ms-playwright
+      - /etc/localtime:/etc/localtime:ro
+    ports:
+      - "3003:3003"
+    command: >
+      bash -c "
+        echo 'Installing dependencies...' &&
+        npx -y playwright@1.52.0 install --with-deps chromium &&
+        echo 'Starting Playwright browser server...' &&
+        npx -y playwright@1.52.0 run-server \
+          --port 3003 \
+          --host 0.0.0.0
+      "
+    networks:
+      - ai_network
+    # Kui soovid, et Tailscale ka seda näeks (soovitatav)
+    #depends_on:
+    #  - ts-network
+
+networks:
+  ai_network:
+    external: true
+    name: main_ai_network

+ 45 - 0
third/n8n/n8n-custom-runner/Dockerfile

@@ -0,0 +1,45 @@
+# Stage 1: Install Chromium and dependencies in a full Alpine image
+FROM alpine:3.22 AS chromium-installer
+RUN apk add --no-cache \
+    chromium \
+    nss \
+    freetype \
+    freetype-dev \
+    harfbuzz \
+    ca-certificates \
+    ttf-freefont \
+    font-noto-emoji \
+    wqy-zenhei
+
+# Stage 2: Copy Chromium and dependencies to the n8n runners image
+FROM n8nio/runners:latest
+
+USER root
+
+# Copy Chromium binary, libraries, and fonts from the installer stage
+COPY --from=chromium-installer /usr/bin/chromium /usr/bin/chromium
+COPY --from=chromium-installer /usr/lib/chromium/ /usr/lib/chromium/
+COPY --from=chromium-installer /usr/lib/libnss*.so* /usr/lib/
+COPY --from=chromium-installer /usr/lib/libfreetype*.so* /usr/lib/
+COPY --from=chromium-installer /usr/lib/libharfbuzz*.so* /usr/lib/
+COPY --from=chromium-installer /usr/share/fonts/ /usr/share/fonts/
+COPY --from=chromium-installer /etc/fonts/ /etc/fonts/
+
+# Install JavaScript packages for utilities and scraping
+RUN cd /opt/runners/task-runner-javascript && \
+    pnpm add moment uuid lodash dotenv axios got node-fetch puppeteer playwright cheerio jsdom xml2js jsonpath yaml form-data
+
+# Configure Playwright to use system Chromium instead of downloading browsers
+# This is necessary because Playwright's bundled browsers don't work well with Alpine's musl libc
+ENV PLAYWRIGHT_SKIP_BROWSER_DOWNLOAD=1
+ENV PLAYWRIGHT_CHROMIUM_EXECUTABLE_PATH=/usr/bin/chromium
+
+# Install Python packages for utilities and scraping
+RUN cd /opt/runners/task-runner-python && \
+    uv pip install requests httpx aiohttp beautifulsoup4 lxml lxml[html_clean] selenium scrapy requests-html mechanize pyquery html5lib cssselect parsel pandas numpy jsonpath-ng pyyaml toml python-dotenv environs python-dateutil arrow pytz pendulum validators email-validator phonenumbers iso8601 websocket-client sickle selenium
+
+# Copy the launcher config file
+#COPY docker/runners/n8n-task-runners.json /etc/n8n-task-runners.json
+COPY ./n8n-task-runners.json  /etc/n8n-task-runners.json
+
+USER runner

+ 58 - 0
third/n8n/n8n-custom-runner/n8n-task-runners.json

@@ -0,0 +1,58 @@
+{
+  "task-runners": [
+    {
+      "runner-type": "javascript",
+      "workdir": "/home/runner",
+      "command": "/usr/local/bin/node",
+      "args": [
+        "--disallow-code-generation-from-strings",
+        "--disable-proto=delete",
+        "/opt/runners/task-runner-javascript/dist/start.js"
+      ],
+      "health-check-server-port": "5681",
+      "allowed-env": [
+        "PATH",
+        "GENERIC_TIMEZONE",
+        "NODE_OPTIONS",
+        "N8N_RUNNERS_AUTO_SHUTDOWN_TIMEOUT",
+        "N8N_RUNNERS_TASK_TIMEOUT",
+        "N8N_RUNNERS_MAX_CONCURRENCY",
+        "N8N_SENTRY_DSN",
+        "N8N_VERSION",
+        "ENVIRONMENT",
+        "DEPLOYMENT_NAME"
+      ],
+      "env-overrides": {
+        "NODE_FUNCTION_ALLOW_BUILTIN": "*",
+        "NODE_FUNCTION_ALLOW_EXTERNAL": "moment,uuid,lodash,dotenv,axios,got,node-fetch,puppeteer,playwright,cheerio,jsdom,xml2js,jsonpath,yaml,form-data",
+        "N8N_RUNNERS_HEALTH_CHECK_SERVER_HOST": "0.0.0.0"
+      }
+    },
+    {
+      "runner-type": "python",
+      "workdir": "/home/runner",
+      "command": "/opt/runners/task-runner-python/.venv/bin/python",
+      "args": [
+        "-m",
+        "src.main"
+      ],
+      "health-check-server-port": "5682",
+      "allowed-env": [
+        "PATH",
+        "N8N_RUNNERS_LAUNCHER_LOG_LEVEL",
+        "N8N_RUNNERS_AUTO_SHUTDOWN_TIMEOUT",
+        "N8N_RUNNERS_TASK_TIMEOUT",
+        "N8N_RUNNERS_MAX_CONCURRENCY",
+        "N8N_SENTRY_DSN",
+        "N8N_VERSION",
+        "ENVIRONMENT",
+        "DEPLOYMENT_NAME"
+      ],
+      "env-overrides": {
+        "PYTHONPATH": "/opt/runners/task-runner-python",
+        "N8N_RUNNERS_STDLIB_ALLOW": "*",
+        "N8N_RUNNERS_EXTERNAL_ALLOW": "requests,httpx,aiohttp,beautifulsoup4,bs4,lxml,selenium,scrapy,requests-html,mechanize,pyquery,html5lib,cssselect,parsel,pandas,numpy,jsonpath-ng,pyyaml,toml,dotenv,environs,python-dateutil,arrow,pytz,pendulum,validators,email-validator,phonenumbers,iso8601,websocket,sickle,selenium"
+      }
+    }
+  ]
+}

+ 19 - 0
third/n8n/run.sh

@@ -0,0 +1,19 @@
+#!/bin/bash
+
+#docker-compose up -d
+#sleep 5
+# Playwright node installimine
+#docker exec -it n8n npm install n8n-nodes-playwright
+
+#docker exec -it n8n sh -c "ls /";
+#docker exec -it -u 0 n8n npm install -g playwright
+
+
+docker-compose down
+#docker-compose build n8n-runners
+docker build -t n8n-runner-custom n8n-custom-runner/
+sleep 1
+docker-compose up -d
+
+
+exit 0

+ 141 - 0
third/server/anythingllm/LOEMIND.md

@@ -0,0 +1,141 @@
+# AnythingLLM – Docker kasutusjuhend
+
+Dokumentide põhine LLM vestlusrobot (RAG – oma failidest küsimiseks).
+
+## Arhitektuur
+
+| Komponent | Asukoht | Ühendus |
+|-----------|---------|---------|
+| **AnythingLLM** | Docker konteiner (`anythingllm`) | port 3002 |
+| **Ollama** (LLM) | Native systemd teenus | `host.docker.internal:11434` |
+| **Ollama** (embedding) | Native systemd teenus | `host.docker.internal:11434` |
+| **Qdrant** | Docker konteiner (`qdrant`) | `host.docker.internal:6333` |
+| **GPU** | ROCm 7.2.2, gfx1151 (Radeon 8060S) | hostil |
+
+**NB!** Ollama EI OLE Dockeris – see jookseb native systemd teenusena koos ROCm GPU toega.
+Ühendus toimub läbi `host.docker.internal:11434`.
+
+## Seadistus
+
+Kasutab:
+- **Ollama** (native) – LLM mudel (`qwen3:30b-fast`, 18 GB)
+- **Ollama** (native) – embedding mudel (`nomic-embed-text:latest`, GPU, 274 MB)
+- **Qdrant** – vektorbaas (`host.docker.internal:6333`)
+
+Compose faili olulised keskkonnamuutujad:
+- `LLM_PROVIDER=ollama` – LLM läbi ollama
+- `OLLAMA_BASE_PATH=http://host.docker.internal:11434` – native ollama
+- `OLLAMA_MODEL_PREF=qwen3:30b-fast` – LLM mudel
+- `EMBEDDING_ENGINE=ollama` – embedding läbi ollama
+- `EMBEDDING_MODEL_PREF=nomic-embed-text:latest` – GPU embedding
+- `VECTOR_DB=qdrant` – vektorbaasi tüüp
+- `SETUP=false` – süsteem juba seadistatud
+
+**NB!** Mudelit saab igal ajal muuta AnythingLLM veebiliidese kaudu (Settings → LLM / Embedder).
+Compose failis olev mudelinimi on ainult algseadistuse jaoks.
+
+## Docker käsud
+
+```bash
+# Ava kaust
+cd /opt/docker-compose/third/server/anythingllm/
+
+# Käivita
+docker-compose up -d
+
+# Peata
+docker-compose down
+
+# Taaskäivita
+docker-compose restart
+
+# Logid
+docker-compose logs -f
+
+# Uuenda
+docker-compose pull
+docker-compose up -d
+```
+
+## Docker otse
+
+```bash
+# Konteineri seis
+docker ps | grep anythingllm
+
+# Logid
+docker logs anythingllm
+
+# Taaskäivita
+docker restart anythingllm
+
+# Kontrolli ollama ühendust
+docker exec anythingllm curl -s http://host.docker.internal:11434/api/tags
+```
+
+## Ligipääs
+
+| Teenus | Port | URL |
+|--------|------|-----|
+| AnythingLLM UI | 3002 | http://100.87.1.24:3002 |
+
+## Sisselogimine
+
+- **Kasutaja:** ardo
+- **Parool:** dwNs55RkiwSEC3TxQG0P
+
+## Olulised kataloogid
+
+| Asukoht | Sisu |
+|---------|------|
+| `/opt/docker-compose/third/server/anythingllm/` | Compose failid ja see dokument |
+| `/data/docker/anythingllm/storage` | Andmebaas, dokumendid, seadistused |
+| `/data/docker/anythingllm/logs` | Logid |
+| `/backups/docker/anythingllm` | Varukoopiad |
+
+## Võrguinfo
+
+- Konteiner on `main_ai_network` peal (compose'is `ai_network`)
+- Ligipääs Ollamale ja Qdrantile läbi `host.docker.internal`
+- `extra_hosts: host.docker.internal:host-gateway` on compose failis seadistatud
+
+## Vead ja tõrkeotsing
+
+### Ei ühendu Ollamaga
+```bash
+# Testi ollama API-t
+curl http://100.87.1.24:11434/api/tags
+
+# Testi konteineri seest
+docker exec anythingllm curl -s http://host.docker.internal:11434/api/tags
+
+# Kontrolli compose faili
+grep OLLAMA /opt/docker-compose/third/server/anythingllm/docker-compose.yml
+```
+
+### Embedding aeglane
+- Kontrolli, et `EMBEDDING_MODEL_PREF=nomic-embed-text:latest` (GPU versioon)
+- Kontrolli ollama GPU olekut: `ollama ps` peaks näitama "100% GPU"
+- Kui mudel pole laetud, tee üks embedding päring UI kaudu
+
+### Andmebaasi lähtestamine
+Kui on vaja kõik andmed kustutada ja otsast alustada:
+```bash
+# Peata konteiner
+docker-compose -f /opt/docker-compose/third/server/anythingllm/docker-compose.yml down
+
+# Kustuta storage (ETTEVAATUST – kustutab KÕIK)
+sudo rm -rf /data/docker/anythingllm/storage/*
+
+# Muuda compose failis SETUP=true (esmaseks seadistuseks)
+# Käivita uuesti
+docker-compose -f /opt/docker-compose/third/server/anythingllm/docker-compose.yml up -d
+```
+
+## Ajalugu
+
+| Kuupäev | Muudatus |
+|---------|----------|
+| 2025-07-05 | Konteiner viidud otse `docker run` pealt compose haldusesse |
+| 2025-07-05 | `SETUP=true` → `false` (süsteem juba seadistatud) |
+| 2025-07-05 | Ollama viidud native peale – ühendus `host.docker.internal:11434` |

Some files were not shown because too many files changed in this diff