إطار الويب الشبيه بـ Sinatra لـ NIM. يوفر Jester DSL لإنشاء تطبيقات الويب بسرعة في NIM.
# example.nim
import htmlgen
import jester
routes:
get " / " :
resp h1 ( " Hello world " )تجميع وتشغيل مع:
cd tests/example
nim c -r example.nim
عرض في: LocalHost: 5000
قبل النشر في الإنتاج ، تأكد من تشغيل التطبيق الخاص بك خلف وكيل عكسي. لم يتم تصلب هذه المكتبة بعد ضد مآثر أمان HTTP ، لذا لا ينبغي أن تتعرض الطلبات المكتوبة فيها للإنترنت العام.
routes:
get " / " :
# do something here. يجب أن تكون جميع الطرق داخل كتلة routes .
سيتم تنفيذ الطرق بالترتيب الذي تم الإعلان عنه. لذا كن حذرًا عند التوقف.
قد يحتوي مسار الطريق على نمط خاص أو مجرد سلسلة ثابتة. الأنماط الخاصة متطابقة تقريبًا مع سيناترا ، والفرق الحقيقي الوحيد هو استخدام @ بدلاً من : .
get " /hello/@name " :
# This matches "/hello/fred" and "/hello/bob".
# In the route ``@"name"`` will be either "fred" or "bob".
# This can of course match any value which does not contain '/'.
resp " Hello " & @ " name "الأنماط في Jester هي حاليًا أكثر محدودة قليلاً ، لا توجد أنماط البرية.
يمكنك استخدام "؟" حرف للدلالة على أجزاء المسار الاختيارية.
get " /hello/@name? " :
# This will match what the previous code example matches but will also match
# "/hello/".
if @ " name " == " " :
resp " No name received :( "
else :
resp " Hello " & @ " name "في هذه الحالة ، قد ترغب في إنشاء "/" اختياريًا أيضًا ، يمكنك القيام بذلك عن طريق تغيير النمط إلى "/hello/؟@name؟". هذا مفيد لأن Jester لن يتطابق مع "/Hello" إذا لم يتم صنعه اختياريًا.
يمكن أيضًا استخدام Regex كنمط طريق. سيتم وضع التقاطات الفرعية عند request.matches . على سبيل المثال:
get re " ^ /([0-9]{2}) .html$ " :
resp request.matches[ 0 ] هذا سوف يتطابق مع عناوين URL من النموذج /15.html . في هذه الحالة ، سيكون request.matches[0] هو 15 .
يدعم Jester الظروف ، ومع ذلك فهي تقتصر على قالب cond البسيط.
routes:
get " /@name " :
cond @ " name " == " daniel "
# ``cond`` will pass execution to the next matching route if @"name" is not
# "daniel".
resp " Correct, my name is daniel. "
get " /@name " :
# This will be the next route that is matched.
resp " No, that's not my name. " جميع أجساد الطريق لها كائن request ضمني. تم توثيق هذا الكائن في jester.nim ويمكن إنشاء الوثائق عن طريق تنفيذ nim doc jester.nim .
يجب أن يتم إعادة استجابة من المسار باستخدام إحدى الوظائف التالية:
resp .body headers و/أو status والاتصال return .redirect وظيفةattachmentقد يكون هناك المزيد. ألق نظرة على وثائق jester.nim لمزيد من المعلومات.
من الممكن عدم استخدام الماكرو routes والقيام بالتوجيه بنفسك.
يمكنك القيام بذلك عن طريق كتابة إجراء match الخاص بك. ألقِ نظرة على example2 للحصول على مثال على كيفية القيام بذلك.
بشكل افتراضي ، يبحث Jester عن الملفات الثابتة في ./public . يمكن تجاوز هذا باستخدام وظيفة setStaticDir . سيتم تقديم الملفات مثل:
./public/css/style.css -> http://example.com/css/style.css
ملاحظة : سوف يخدم Jester الملفات فقط ، والتي يمكن قراءة others . على UNIX/Linux ، يمكنك التأكد من ذلك باستخدام chmod o+r ./public/css/style.css .
يمكن تعيين ملفات تعريف الارتباط باستخدام وظيفة setCookie .
get " / " :
# Set a cookie "test:value" and make it expire in 5 days.
setCookie ( " test " , @ " value " , daysForward ( 5 )) يمكن بعد ذلك الوصول إليها باستخدام إجراء request.cookies الذي يقوم بإرجاع Table[string, string] .
يحتفظ كائن الطلب بجميع المعلومات حول الطلب الحالي. يمكنك الوصول إليه من مسار باستخدام متغير request . يتم تعريفه على النحو التالي:
Request * = ref object
params * : StringTableRef # # Parameters from the pattern, but also the
# # query string.
matches * : array [ MaxSubpatterns , string ] # # Matches if this is a regex
# # pattern.
body * : string # # Body of the request, only for POST.
# # You're probably looking for ``formData``
# # instead.
headers * : StringTableRef # # Headers received with the request.
# # Retrieving these is case insensitive.
formData * : MultiData # # Form data; only present for
# # multipart/form-data
port * : int
host * : string
appName * : string # # This is set by the user in ``run``, it is
# # overriden by the "SCRIPT_NAME" scgi
# # parameter.
pathInfo * : string # # This is ``.path`` without ``.appName``.
secure * : bool
path * : string # # Path of request.
query * : string # # Query string of request.
cookies * : StringTableRef # # Cookies from the browser.
ip * : string # # IP address of the requesting client.
reqMeth * : HttpMethod # # Request method, eg. HttpGet, HttpPost
settings * : Settings يسمح جهاز التوجيه المخصص لتشغيل رمز التهيئة الخاص بك وتمرير الإعدادات الديناميكية إلى Jester قبل بدء حلقة Async.
import asyncdispatch, jester, os, strutils
router myrouter:
get " / " :
resp " It's alive! "
proc main () =
let port = paramStr ( 1 ). parseInt (). Port
let settings = newSettings (port = port)
var jester = initJester (myrouter, settings = settings)
jester. serve ()
when isMainModule :
main ()يشبه رمز هذا إلى حد كبير رمز Sinatra الوارد هنا: http://help.github.com/post-receive-hooks/
import jester, json
routes:
post " / " :
var push = parseJson ( @ " payload " )
resp " I got some JSON: " & $ push