LOOK, framework olmadan web uygulaması yazmanın en sade yolu. Apache'ye at, çalış — terminal yok, config yok.
# DB bağlantısı — bir kez, warm start ile kalıcı $conn = db::connect("mysql://root:@127.0.0.1/blog"); # Routing dile gömülü — framework yok route("GET", "/", function() use ($conn) { $yazilar = db::query($conn, "SELECT * FROM yazilar ORDER BY id DESC LIMIT 10", []); print(json::encode(["ok" => true, "data" => $yazilar])); }); route("POST", "/yazi/{id}/begeni", function($id) use ($conn) { db::exec($conn, "UPDATE yazilar SET begeni=begeni+1 WHERE id=?", [int($id)]); print(json::encode(["ok" => true])); }); route("404", function() { response::status(404); print(json::encode(["ok" => false, "hata" => "Bulunamadı"])); });
looktest.tobiyo.com.tr üzerinde AlmaLinux 8, MariaDB, 32 worker ile ölçüldü.
Tüm testler looktest.tobiyo.com.tr canlı ortamında,
wrk / ab ile bağımsız olarak ölçülmüştür.
DB-bound endpoint'ler ~380 RPS — darboğaz MySQL RTT (~2.6ms), LOOK değil.
Framework kurmadan, paket yüklemeden doğrudan yazın.
route("GET", "/urun/{id}", fn) — tek satır, framework yok, Express yok, Laravel yok.
Sıfır bağımlılık, wire protocol doğrudan. Aynı API: db::query / db::exec.
route("WS", "/chat", fn) — chat, canlı veri, bildirimleri tek dosyada yaz.
Go goroutine stili eşzamanlılık — 3 paralel DB sorgusu, fan-out pattern, pipeline.
AST → register-based bytecode → switch dispatch. Compute-heavy workload'da 7.8× hız.
DB bağlantısı bir kez açılır, her istekte yeniden kullanılır. Sıfır connection overhead.
cache:: · queue:: · jobs:: · mail:: · template:: · auth:: · validator:: — hepsi dahil.
look test ile 10 assertion built-in. look repl ile interaktif geliştirme.
use "routes/auth.lk" — Go paketi gibi, sadece fonksiyonlar export, $var izolasyonu.
$conn = db::connect("mysql://root:@127.0.0.1/blog"); use auth; use validator; function admin_kontrol() { session::start(); if (session::get("admin_id") == null) { response::status(401); print(json::encode(["ok" => false, "hata" => "Yetkisiz"])); return false; } return true; } route("GET", "/api/yazilar", function() use ($conn) { $rows = db::query($conn, "SELECT * FROM yazilar ORDER BY id DESC", []); print(json::encode(["ok" => true, "data" => $rows])); }); route("POST", "/api/yazilar", function() use ($conn) { if (!admin_kontrol()) { return; } $v = validator::check(request::json(), [ "baslik" => ["required", "min:3", "max:200"], "icerik" => ["required", "min:10"] ]); if (!$v["ok"]) { response::status(422); print(json::encode($v)); return; } $data = request::json(); db::exec($conn, "INSERT INTO yazilar (baslik,icerik) VALUES (?,?)", [$data["baslik"], $data["icerik"]]); print(json::encode(["ok" => true, "id" => db::last_id($conn)])); });
# --mode http ile çalışır $hub = channel(); # broadcast kanalı route("WS", "/chat", function($ws) use ($hub) { # Gelen mesajları bu client'a ilet parallel(function() use ($ws, $hub) { while (true) { $msg = receive($hub); if ($msg == null) { break; } ws::send($ws, $msg); } }); # Mesaj gelince hub'a gönder → tüm clientlar duyar ws::on($ws, "message", function($data) use ($hub) { $p = json::decode($data); send($hub, json::encode([ "from" => request::ip(), "msg" => $p["msg"] ])); }); ws::on($ws, "close", function() { log::info("Chat bağlantısı kapandı"); }); }); # 30s keepalive ping — SSE ile aynı pattern timer::every(30000, function() { ws::broadcast(json::encode(["type" => "ping"])); });
$conn = db::connect("mysql://root:@127.0.0.1/qrmenu"); route("GET", "/panel/ozet", function() use ($conn) { # 3 sorguyu paralel çalıştır — toplam süre max(t1,t2,t3) $ch = channel(3); parallel(function() use ($ch, $conn) { send($ch, db::col($conn, "SELECT count(*) FROM firmalar", [])); }); parallel(function() use ($ch, $conn) { send($ch, db::col($conn, "SELECT count(*) FROM urunler", [])); }); parallel(function() use ($ch, $conn) { send($ch, db::col($conn, "SELECT count(*) FROM kategoriler", [])); }); $firmalar = receive($ch); $urunler = receive($ch); $kategoriler = receive($ch); print(json::encode([ "firmalar" => $firmalar, "urunler" => $urunler, "kategoriler" => $kategoriler ])); });
use jobs; use mail; # Route: isteği anında yanıtla, işi kuyruğa at route("POST", "/kayit", function() use ($conn) { $data = request::json(); db::exec($conn, "INSERT INTO kullanicilar (email,ad) VALUES (?,?)", [$data["email"], $data["ad"]]); # Kuyruğa at — max 3 deneme, hemen çalıştır jobs::push("hosgeldin_email", [ "to" => $data["email"], "ad" => $data["ad"] ], 3, 0); print(json::encode(["ok" => true])); }); # worker.lk — ayrı process (systemd servisi) jobs::recover("hosgeldin_email"); # crash recovery jobs::worker("hosgeldin_email", function($job) { $r = mail::send( $job["payload"]["to"], "Hoş geldiniz!", "Merhaba " . $job["payload"]["ad"] . ", kaydınız tamamlandı." ); return $r["ok"]; # false → retry (max 3) }); jobs::run(5000); # 5 saniyede bir — blocking
use template; struct Yazi { id baslik icerik tarih begeni: 0 } $tpl = env("VIEWS_DIR", "/app/views"); route("GET", "/blog", function() use ($conn, $tpl) { $rows = db::query($conn, "SELECT * FROM yazilar", []); print(template::render($tpl . "/blog/index", [ "baslik" => "Blog", "yazilar" => $rows ])); }); # views/blog/index.html: # {#extends "views/layout/base"} # {#block "content"} # {#each $yazilar as $y} # <h2>{$y.baslik}</h2> # {/each} # {/block}
| Özellik | PHP 8.x | LOOK |
|---|---|---|
| Routing | Framework gerekir | Dile gömülü |
| DB bağlantısı | Her request'te yeniden | Warm start — bir kez |
| Global değişken | $_GET, $_POST, $_SESSION... | Yok — request::, session:: |
| WebSocket | Ek kütüphane (Ratchet/Swoole) | Yerleşik |
| Goroutine / async | Yok (veya Swoole) | parallel() + channel() |
| Bellek (32 worker) | ~1.8 GB (Apache) | 8 MB |
| Karma array | İzin verilir (karışıklık) | Kasıtlı yok |
| Closure capture | use() zorunlu değil | use() zorunlu — temiz |
| Deployment | Apache/cgi | Apache/cgi + HTTP server |
Platform seçin:
Ubuntu 22/24 veya AlmaLinux 8 — distro otomatik algılanır.
curl -fsSL https://get.codlook.com | sudo bash
Kurulum scripti Apache/nginx config'i otomatik yazar. Sadece restart:
systemctl restart apache2 # veya httpd
/var/www/html/index.lk dosyasını oluştur, tarayıcıda aç — bitti.
look version # LOOK 1.0.0 (linux/amd64)
XAMPP zaten kuruluysa bu adımı atlayın.
https://www.apachefriends.org/
Binary'leri kopyalar, Apache'yi yapılandırır, Windows servisi olarak kaydeder.
install.bat --xampp C:\xampp
XAMPP Control Panel → Apache → Stop → Start. Ardından tarayıcıda http://localhost/saglik açın.
Plesk → Extensions → ZIP Yükle → look-lang-1.0.0.zip seçin.
LOOK → Domain Ekle → domain seç, script yolu yaz, worker sayısı seç → Başlat.
Terminal yok. SSH yok. Config yok. systemd servisi ve nginx vhost otomatik oluşturuldu.
v1.0.0 — Tüm platformlar için kararlı sürüm.
Ubuntu 22/24, AlmaLinux 8, Debian 11/12. x86_64 + ARM64.
curl -fsSL https://get.codlook.com | sudo bash
Windows 10/11 + XAMPP. IOCP — sınırsız bağlantı. Task Scheduler ile otomatik başlatma.
⇓ look-windows-x64.zip install.bat (XAMPP)Plesk 18+ için tek tıkla kurulum. Domain ekle, başlat — terminal yok.
⇓ look-lang-1.0.0.zip GitHub →Sözdizimi renklendirme, snippet'lar, bracket matching. v0.2.1
Marketplace → VSIX (offline)