Uses 2770K of libraries. Compilation Failed (26044L/142K).
1 | !7 |
2 | |
3 | concept Domain {
|
4 | S domain; |
5 | S moduleLibID; |
6 | S proxyDestination; |
7 | S proxyCookieChecker; // a module lib ID |
8 | bool mustBeEnabled; |
9 | |
10 | toString { ret super.toString() + " " + domain; }
|
11 | } |
12 | |
13 | cm Eleu3 > DynEleu {
|
14 | transient CRUD<Domain> domainCRUD; |
15 | switchable bool verbose; |
16 | switchable bool debugNanoHTTPD; |
17 | switchable S sameSite; |
18 | |
19 | start {
|
20 | NanoHTTPD_debug = debugNanoHTTPD; |
21 | useDBOf(#1029618); // NOT WORKING?! |
22 | dbIndexingCI(Domain, 'domain); |
23 | uniqCI Domain(domain := "<default>"); |
24 | domainCRUD = new CRUD(Domain); |
25 | dm_registerAs eleuWithCRUD(); |
26 | } |
27 | |
28 | visualize {
|
29 | var c = jtabs( |
30 | "Main", super.visualize(), |
31 | "Domains" := domainCRUD.visualize()); |
32 | |
33 | tablePopupMenu(domainCRUD.table(), voidfunc(JPopupMenu menu, int row) {
|
34 | Domain d = domainCRUD.selected(), ret if null; |
35 | if (nempty(d.moduleLibID)) |
36 | addMenuItem(menu, "Load module", rThreadEnter { dm_makeOrShow(d.moduleLibID) });
|
37 | }); |
38 | |
39 | ret c; |
40 | } |
41 | |
42 | @Override |
43 | S moduleForDomain(S domain) {
|
44 | domain = dropAfterColon(domain); // drop port number |
45 | for (Domain d : domainsInMatchingOrder()) {
|
46 | if (matchingDomain(d, domain)) {
|
47 | S mod = findMod(d); |
48 | if (verbose) print("Domain matched: " + domain + " / " + d.domain + " => " + mod);
|
49 | try answer mod; |
50 | } else |
51 | if (verbose) print("Domain not matched: " + domain + " / " + d.domain);
|
52 | } |
53 | ret findMod(defaultDomain()); |
54 | } |
55 | |
56 | Domain defaultDomain() {
|
57 | ret conceptWhereCI Domain(domain := "<default>"); |
58 | } |
59 | |
60 | S findMod(Domain d) {
|
61 | if (d == null || empty(d.moduleLibID)) null; |
62 | ret d.mustBeEnabled |
63 | ? dm_findModuleWithParams(d.moduleLibID, enabled := true) |
64 | : dm_findModule(d.moduleLibID); |
65 | } |
66 | |
67 | ServeHttp_CookieHandler makeCookieHandler() {
|
68 | ServeHttp_CookieHandler cookieHandler = super.makeCookieHandler(); |
69 | cookieHandler.metaParams = appendPrefixIfNempty("SameSite=", sameSite);
|
70 | ret cookieHandler; |
71 | } |
72 | |
73 | void onWebServersStarted :: after {
|
74 | forEach(webServers(), ws -> {
|
75 | print("Augmenting web server: " + ws);
|
76 | |
77 | ws.collectHeaderLines = true; |
78 | |
79 | // session is an instance of NanoHTTPD.IHTTPSession |
80 | ws.specialHandling = session -> ctex {
|
81 | temp enter(); |
82 | S domain = dropPortFromHost(mapGet(session.getHeaders(), "host")); |
83 | |
84 | Domain d = first(domainsInMatchingOrder(), |
85 | _d -> matchingDomain(_d, domain)); |
86 | |
87 | printVars(+domain, +d); |
88 | if (d == null || empty(d.proxyDestination)) false; |
89 | print("Handling proxy request to " + d.proxyDestination);
|
90 | HostAndPort hap = new(d.proxyDestination); |
91 | |
92 | if (nempty(d.proxyCookieChecker)) {
|
93 | S cookieChecker = dm_findModule(d.proxyCookieChecker); |
94 | if (empty(cookieChecker)) |
95 | fail(print("Cookie checker " + d.proxyCookieChecker + " not found, aborting request"));
|
96 | |
97 | NanoHTTPD.CookieHandler cookies = session.getCookies(); |
98 | |
99 | if (!isTrue(dm_call(cookieChecker, "checkCookie", cookies.read("cookie"), domain)))
|
100 | fail(print("Cookie checker disapproves"));
|
101 | } |
102 | |
103 | S headers = windowsLineBreaks(lines(concatLists( |
104 | ll(session.getMethod() + " " + session.getFullURI() + " " + session.getProtocolVersion()), |
105 | session.getHeaderLines() |
106 | ))); |
107 | |
108 | new StandaloneHttpProxy proxy; |
109 | proxy.rewriteHostHeader = false; |
110 | proxy.forwardServerAndPort = req -> hap; |
111 | proxy.takeOverIncomingSocket(session.getSocket(), |
112 | session.getInputStream(), |
113 | session.getOutputStream(), |
114 | toUtf8(printQuoted("HEADERS: ", headers))
|
115 | ); |
116 | true; |
117 | }; |
118 | }); |
119 | } // onWebServersStarted |
120 | |
121 | bool matchingDomain(Domain d, S domain) {
|
122 | ret domainIsUnder_extended(domain, d.domain); |
123 | } |
124 | |
125 | // API |
126 | |
127 | Cl<Domain> domainsInMatchingOrder() {
|
128 | ret sortByCalculatedFieldICDesc( |
129 | filter(list(Domain), d -> !eqic(d.domain, "<default>")), |
130 | d -> reversed(d.domain)); |
131 | } |
132 | |
133 | void addDomain(S domain, S moduleLibID, bool mustBeEnabled) {
|
134 | uniq Domain(+domain, +moduleLibID, +mustBeEnabled); |
135 | } |
136 | } |
Began life as a copy of #1029618
download show line numbers debug dex old transpilations
Travelled to 3 computer(s): bhatertpkbcr, mowyntqkapby, mqqgnosmbjvj
No comments. add comment
| Snippet ID: | #1032719 |
| Snippet name: | Eleu/CRUD/domain-based v2 - main web server module [moved to #1029618] |
| Eternal ID of this version: | #1032719/29 |
| Text MD5: | 0747e347f1af84733e8d3e693625af1b |
| Transpilation MD5: | de25fd6911d3316baaa2b15c61df0d42 |
| Author: | stefan |
| Category: | javax |
| Type: | JavaX source code (Dynamic Module) |
| Public (visible to everyone): | Yes |
| Archived (hidden from active list): | No |
| Created/modified: | 2021-10-03 23:15:08 |
| Source code size: | 4317 bytes / 136 lines |
| Pitched / IR pitched: | No / No |
| Views / Downloads: | 489 / 870 |
| Version history: | 28 change(s) |
| Referenced in: | [show references] |