Mercurial Hosting > hghosting
comparison src/lib/Shared.luan @ 0:dfc36e7ed22c
init
author | Vadim Filimonov <fffilimonov@yandex.ru> |
---|---|
date | Thu, 12 May 2022 13:51:59 +0400 |
parents | |
children | 028e74c8889d |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:dfc36e7ed22c |
---|---|
1 local Luan = require "luan:Luan.luan" | |
2 local error = Luan.error | |
3 local ipairs = Luan.ipairs or error() | |
4 local pairs = Luan.pairs or error() | |
5 local type = Luan.type or error() | |
6 local set_metatable = Luan.set_metatable or error() | |
7 local stringify = Luan.stringify or error() | |
8 local parse = Luan.parse or error() | |
9 local range = Luan.range or error() | |
10 local String = require "luan:String.luan" | |
11 local split = String.split or error() | |
12 local trim = String.trim or error() | |
13 local sub_string = String.sub or error() | |
14 local Table = require "luan:Table.luan" | |
15 local concat = Table.concat or error() | |
16 local Math = require "luan:Math.luan" | |
17 local random = Math.random or error() | |
18 local Binary = require "luan:Binary.luan" | |
19 local binary_base64_decode = Binary.base64_decode or error() | |
20 local binary_to_string = Binary.to_string or error() | |
21 local Io = require "luan:Io.luan" | |
22 local uri = Io.uri or error() | |
23 local Http = require "luan:http/Http.luan" | |
24 local Logging = require "luan:logging/Logging.luan" | |
25 local logger = Logging.logger "Shared" | |
26 | |
27 | |
28 local Shared = {} | |
29 | |
30 function Shared.head() | |
31 %> | |
32 <meta name="viewport" content="width=device-width, initial-scale=1"> | |
33 <style> | |
34 @import "/site.css"; | |
35 </style> | |
36 <% | |
37 end | |
38 | |
39 local function header(crumbs) | |
40 %> | |
41 <div header> | |
42 <a href="/">Mercurial Hosting</a> | |
43 <% for _, crumb in ipairs(crumbs or {}) do %> | |
44 / <%=crumb%> | |
45 <% end %> | |
46 </div> | |
47 <% | |
48 end | |
49 Shared.header = header | |
50 | |
51 function Shared.admin_header() | |
52 header{ | |
53 [[<a href="/admin/">Your Repositories</a>]] | |
54 } | |
55 end | |
56 | |
57 function Shared.private_header() | |
58 header{ | |
59 [[<a href="/private/">private</a>]] | |
60 [[<a href="/private/tools/">tools</a>]] | |
61 } | |
62 end | |
63 | |
64 Shared.admin_return = [[<p>Return to <a href="/admin/">Your Repositories</a></p>]] | |
65 | |
66 local function base64_decode(s) | |
67 return binary_to_string(binary_base64_decode(s)) | |
68 end | |
69 | |
70 function Shared.get_user() | |
71 local s = Http.request.headers["Authorization"] or error "not authorized" | |
72 local tp, auth = split(s," ") | |
73 tp=="Basic" or error("invalid auth type: "..tp) | |
74 s = base64_decode(auth) | |
75 s = split(s,":") | |
76 return s | |
77 end | |
78 | |
79 local function deep_copy(tbl) | |
80 local t = {} | |
81 for k,v in pairs(tbl) do | |
82 if type(v)=="table" then | |
83 v = deep_copy(v) | |
84 end | |
85 t[k] = v | |
86 end | |
87 return t | |
88 end | |
89 | |
90 local set_mt = {} | |
91 function set_mt.__index(table,key) | |
92 return false | |
93 end | |
94 | |
95 local function list_to_set(list) | |
96 local set = {} | |
97 for _, v in ipairs(list) do | |
98 set[v] = true | |
99 end | |
100 set_metatable(set,set_mt) | |
101 return set | |
102 end | |
103 Shared.list_to_set = list_to_set | |
104 | |
105 function Shared.text_to_list(text) | |
106 local list = {} | |
107 for line in Io.schemes.string(text).read_lines() do | |
108 line = trim(line) | |
109 if line ~= "" then | |
110 list[#list+1] = line | |
111 end | |
112 end | |
113 return list | |
114 end | |
115 | |
116 local password_chars = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" | |
117 do | |
118 local t = {} | |
119 for i in range(1,#password_chars) do | |
120 t[#t+1] = sub_string(password_chars,i,i) | |
121 end | |
122 password_chars = t | |
123 end | |
124 | |
125 function Shared.new_password() | |
126 local n = #password_chars | |
127 local t = {} | |
128 for _ in range(1,10) do | |
129 t[#t+1] = password_chars[random(n)] | |
130 end | |
131 return concat(t) | |
132 end | |
133 | |
134 local raw_config = parse( uri("file:config/config.luano").read_text() ) | |
135 local config = deep_copy(raw_config) | |
136 for name, repo in pairs(config.repos) do | |
137 repo.name = name | |
138 repo.users = list_to_set(repo.users) | |
139 repo.admins = list_to_set(repo.admins) | |
140 end | |
141 config.private = config.private and list_to_set(config.private) | |
142 Shared.config = config | |
143 | |
144 function Shared.get_raw_config() | |
145 return deep_copy(raw_config) | |
146 end | |
147 | |
148 local function reload_nginx() | |
149 local cmd = [[sudo $(which nginx) -s reload]] | |
150 local s = uri("bash:"..cmd).read_text() | |
151 logger.info("reload_nginx "..s) | |
152 end | |
153 | |
154 function Shared.save_raw_config(raw_config) | |
155 local config_file = uri("file:config/config.luano") | |
156 local config_old = uri("file:config/config.luano.old") | |
157 config_old.delete() | |
158 config_file.move_to(config_old) | |
159 config_file.write_text(stringify(raw_config).."\n") | |
160 Http.reset_luan() | |
161 Luan.do_file "update_repositories.luan" | |
162 reload_nginx() | |
163 end | |
164 | |
165 return Shared |