Skip to content

JustL0/image-server

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

2 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

image-server

Basit, güvenli ve yalnızca .png dosyaları servis eden bir HTTPS statik görsel sunucusu.
Fastify üzerinde çalışır; hostname whitelist, streaming, ETag/Last-Modified ve şüpheli istek loglama özelliklerine sahiptir.

Öne Çıkanlar

  • 🔒 HTTPS (kendi sertifikanızı kullanın)
  • 🧰 Host whitelist (Host / X-Forwarded-Host doğrulaması)
  • 📦 Streaming (daha az bellek tüketimi)
  • 🗃️ ETag + Last-Modified (304 yanıtları, basit cache)
  • 🧯 Path traversal ve uzantı filtrelemesi
  • 📝 logs/access.log içine şüpheli istek logları

İçerik


Gereksinimler

  • Node.js 18+ (önerilen: 20 LTS)
  • npm, pnpm ya da yarn

Proje ESM (ECMAScript Modules) kullanır.


Kurulum

# Projeyi indir
git clone https://github.com/JustL0/image-server.git
cd image-server

# Paketleri kur
npm i

Dizin Yapısı

image-server/
├─ server.js           # ya da server.mjs (ESM)
├─ images/             # .png dosyalarınızı buraya koyun
├─ ssl/
│  ├─ origin.key       # özel anahtar
│  └─ origin.crt       # sertifika (chain ile birlikte)
└─ logs/
   └─ access.log       # şüpheli istek logları (otomatik oluşur)

logs/ klasörü ilk çalıştırmada otomatik yaratılır.


Yapılandırma

Hostname Whitelist

server.js içinde:

const ALLOWED_HOSTS = new Set([
  'subdomain.domain.com',
  'www.domain.com'
  // Lokal test için şunları ekleyebilirsiniz:
  // 'localhost',
  // '127.0.0.1'
]);
  • Sunucu yalnızca bu hostname’lerle gelen istekleri kabul eder.
  • Lokal geliştirme için localhost veya 127.0.0.1 ekleyin (bkz. Geliştirme & Lokal Test).

Sertifikalar

ssl/origin.key ve ssl/origin.crt dosyalarını yerleştirin.
Üretimde gerçek sertifika kullanın. Lokal geliştirmede self-signed oluşturabilirsiniz.

OpenSSL (Git Bash/WSL/WSL2):

openssl req -x509 -newkey rsa:2048 -nodes -keyout ssl/origin.key -out ssl/origin.crt -days 365 \
  -subj "/CN=localhost"

Tarayıcıda uyarı görebilirsiniz; lokalde test için normaldir.

Cache Süresi

Varsayılan: Cache-Control: public, max-age=86400 (1 gün).
server.js içinde ihtiyacınıza göre değiştirin:

.header('Cache-Control', 'public, max-age=86400')

Çalıştırma

node server.mjs

Varsayılan adres:

  • https://0.0.0.0:2096

Başarı mesajı: Image server listening on https://0.0.0.0:2096


Kullanım

  • PNG görüntüleme: GET /<dosya>.png

Örnekler:

  • https://www.domain.com:2096/logo.png
  • https://subdomain.domain.com:2096/path/to/elephant.png

Sadece .png uzantısına izin verilir. Diğer uzantılar (.jpg, .ico, vs.) ve directory traversal denemeleri 404/403 ile sonuçlanır.

HEAD istekleri otomatik desteklenir (Fastify GET için HEAD de üretir).

cURL örnekleri:

# Doğrudan
curl -vk https://subdomain.domain.com:2096/elephant.png -o /dev/null

# Lokal IP ile ama Host header ayarlayarak
curl -vk https://127.0.0.1:2096/elephant.png -H "Host: subdomain.domain.com" -o /dev/null

Loglar

Şüpheli istekler logs/access.log içine yazılır.
Örnek (lokalde görülen çıktı):

2025-09-01T07:11:22.880Z [SUSPICIOUS] reason=invalid_host:127.0.0.1 ip=127.0.0.1 path=/ headers={"host":"127.0.0.1:2096",...}
2025-09-01T07:12:51.192Z [SUSPICIOUS] reason=invalid_host:127.0.0.1 ip=127.0.0.1 path=elephant.png headers={"host":"127.0.0.1:2096",...}
2025-09-01T07:12:58.659Z [SUSPICIOUS] reason=invalid_extension ip=127.0.0.1 path=favicon.ico headers={...}

Olası reason değerleri:

  • invalid_host:<host>: Host whitelist dışı.
  • invalid_extension: .png dışında bir uzantı (örn: favicon.ico).
  • path_traversal: .. vb. ile images/ dışına çıkma denemesi.
  • decode_error: URL decode hatası.
  • stat_error: Dosya bilgisi okunamadı (yok veya izin).
  • read_stream_error: Okuma/stream sırasında hata.
  • invalid_method: GET/HEAD dışındaki HTTP metodu.

Geliştirme & Lokal Test

Tarayıcıyla https://127.0.0.1:2096/elephant.png gibi bir URL açtığınızda Host header 127.0.0.1 olacağı için whitelist’e takılırsınız (logda invalid_host:127.0.0.1 görürsünüz).

Seçenekler:

  1. Whitelist’e ekle

    const ALLOWED_HOSTS = new Set([
      'localhost',
      '127.0.0.1',
      'subdomain.domain.com',
      'www.domain.com'
    ]);
  2. curl ile Host header ayarla

    curl -vk https://127.0.0.1:2096/elephant.png -H "Host: subdomain.domain.com" -o /dev/null
  3. hosts dosyası ile domain → 127.0.0.1

    • Windows: C:\Windows\System32\drivers\etc\hosts
    • Linux/macOS: /etc/hosts

    İçerik örneği:

    127.0.0.1   subdomain.domain.com
    

    Sonra tarayıcıdan: https://subdomain.domain.com:2096/elephant.png


Sık Karşılaşılanlar

  • FST_ERR_DUPLICATED_ROUTE: Method 'HEAD' already declared
    Fastify GET için otomatik HEAD oluşturur. Ekstra fastify.head() yazdıysanız kaldırın ya da Fastify’i exposeHeadRoutes: false ile başlatıp kendi HEAD rotanızı tutun.

  • Tarayıcı favicon.ico istiyor, logda invalid_extension görünüyor
    Sadece .png servis ediliyor. favicon.ico istekleri 404/loglanır. İsterseniz .ico desteği ekleyin veya favicon’u .png olarak verin.

  • Sertifika uyarısı
    Self-signed sertifika lokalde normaldir. Üretimde geçerli sertifika kullanın.


Reverse Proxy/CDN Notları

  • trustProxy: true açıktır. Proxy/CDN arkasında gerçek IP için gereklidir.
  • Host doğrulaması X-Forwarded-HostHost sırasıyla yapılır. Proxy’nizin X-Forwarded-Host’u doğru aktardığından emin olun.
  • CDN/Proxy health check’leri HEAD isteği atabilir; desteklidir.
  • Cloudflare gibi bir CDN kullanıyorsanız, Origin Sertifikası ile ssl/origin.crt/origin.key yerleştirip kullanabilirsiniz.

systemd Servis Örneği

Linux üzerinde servis olarak koşmak için:

/etc/systemd/system/image-server.service

[Unit]
Description=image-server
After=network.target

[Service]
Type=simple
WorkingDirectory=/opt/image-server
ExecStart=/usr/bin/node server.js
Restart=always
User=www-data
Environment=NODE_ENV=production

[Install]
WantedBy=multi-user.target
sudo systemctl daemon-reload
sudo systemctl enable --now image-server
sudo systemctl status image-server

Lisans

MIT

About

A fully configurable http/https image server in NodeJS

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors