1 module temple.vibe;
2 
3 version(Have_vibe_d):
4 
5 pragma(msg, "Compiling Temple with Vibed support");
6 
7 private {
8 	import temple;
9 	import vibe.http.server;
10 	import vibe.textfilter.html;
11 	import std.stdio;
12 	import std.variant;
13 }
14 
15 struct TempleHtmlFilter {
16 
17 	private static struct SafeString {
18 		const string payload;
19 	}
20 
21 	static void temple_filter(ref TempleOutputStream stream, string unsafe) {
22 		filterHTMLEscape(stream, unsafe);
23 	}
24 
25 	static void temple_filter(ref TempleOutputStream stream, Variant variant) {
26 		temple_filter(stream, variant.toString);
27 	}
28 
29 	static string temple_filter(SafeString safe) {
30 		return safe.payload;
31 	}
32 
33 	static SafeString safe(string str) {
34 		return SafeString(str);
35 	}
36 
37 	static SafeString safe(Variant variant) {
38 		return SafeString(variant.toString);
39 	}
40 }
41 
42 private enum SetupContext = q{
43 	static if(is(Ctx == HTTPServerRequest)) {
44 		TempleContext context = new TempleContext();
45 		copyContextParams(context, req);
46 	}
47 	else {
48 		TempleContext context = req;
49 	}
50 };
51 
52 private template isSupportedCtx(Ctx) {
53 	enum isSupportedCtx = is(Ctx : HTTPServerRequest) || is(Ctx == TempleContext);
54 }
55 
56 void renderTemple(string temple, Ctx = TempleContext)
57 	(HTTPServerResponse res, Ctx req = null)
58 	if(isSupportedCtx!Ctx)
59 {
60 	mixin(SetupContext);
61 
62 	auto t = compile_temple!(temple, TempleHtmlFilter);
63 	t.render(res.bodyWriter, context);
64 }
65 
66 void renderTempleFile(string file, Ctx = TempleContext)
67 	(HTTPServerResponse res, Ctx req = null)
68 	if(isSupportedCtx!Ctx)
69 {
70 	mixin(SetupContext);
71 
72 	auto t = compile_temple_file!(file, TempleHtmlFilter);
73 	t.render(res.bodyWriter, context);
74 }
75 
76 void renderTempleLayoutFile(string layout_file, string partial_file, Ctx = TempleContext)
77 	(HTTPServerResponse res, Ctx req = null)
78 	if(isSupportedCtx!Ctx)
79 {
80 	mixin(SetupContext);
81 
82 	auto layout = compile_temple_file!(layout_file, TempleHtmlFilter);
83 	auto partial = compile_temple_file!(partial_file, TempleHtmlFilter);
84 	auto composed = layout.layout(&partial);
85 	composed.render(res.bodyWriter, context);
86 }
87 
88 private void copyContextParams(ref TempleContext ctx, ref HTTPServerRequest req) {
89 
90 	if(!req || !(req.params))
91 		return;
92 
93 	foreach(key, val; req.params) {
94 		ctx[key] = val;
95 	}
96 }