diff --git a/baidudrive/Makefile b/baidudrive/Makefile index 05133f79..8db01848 100644 --- a/baidudrive/Makefile +++ b/baidudrive/Makefile @@ -10,8 +10,8 @@ include $(TOPDIR)/rules.mk PKG_ARCH_BAIDUDRIVE:=$(ARCH) PKG_NAME:=baidudrive -PKG_VERSION:=kaiplus-runtime-v1.0.7 -PKG_RELEASE:=20 +PKG_VERSION:=1.0.6 +PKG_RELEASE:=21 PKG_SOURCE:=$(PKG_NAME)-binary-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/istoreos/istoreos-app-hub/releases/download/baidudrive-runtime-v$(PKG_VERSION)/ PKG_HASH:=skip diff --git a/dockermanager/Makefile b/dockermanager/Makefile index 2aca20ed..a7010347 100644 --- a/dockermanager/Makefile +++ b/dockermanager/Makefile @@ -9,8 +9,8 @@ include $(TOPDIR)/rules.mk PKG_ARCH_DOCKERMANAGER:=$(ARCH) PKG_NAME:=dockermanager -PKG_VERSION:=kaiplus-runtime-v1.0.7 -PKG_RELEASE:=6 +PKG_VERSION:=0.1.1 +PKG_RELEASE:=7 PKG_SOURCE:=$(PKG_NAME)-binary-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/istoreos/istoreos-app-hub/releases/download/dockermanager-runtime-v$(PKG_VERSION)/ PKG_HASH:=skip diff --git a/kaiplus/Makefile b/kaiplus/Makefile index 632c180f..f9c33e82 100644 --- a/kaiplus/Makefile +++ b/kaiplus/Makefile @@ -9,8 +9,8 @@ include $(TOPDIR)/rules.mk PKG_ARCH_kaiplus:=$(ARCH) PKG_NAME:=kaiplus -PKG_VERSION:=kaiplus-runtime-v1.0.7 -PKG_RELEASE:=10 +PKG_VERSION:=1.0.7 +PKG_RELEASE:=11 PKG_SOURCE:=$(PKG_NAME)-binary-$(PKG_VERSION).tar.gz PKG_SOURCE_URL:=https://github.com/istoreos/istoreos-app-hub/releases/download/kaiplus-runtime-v$(PKG_VERSION)/ PKG_HASH:=skip diff --git a/luci-app-kaiplus/Makefile b/luci-app-kaiplus/Makefile index 7f45f618..1b7bf010 100644 --- a/luci-app-kaiplus/Makefile +++ b/luci-app-kaiplus/Makefile @@ -8,8 +8,8 @@ include $(TOPDIR)/rules.mk LUCI_TITLE:=KaiPlus PKG_VERSION:=1.0.7 -PKG_RELEASE:=7 -LUCI_DEPENDS:=+kaiplus +luci-compat +luci-lib-openwrtauth +PKG_RELEASE:=8 +LUCI_DEPENDS:=+kaiplus +luci-compat +luci-lib-linkeaseauth LUCI_MINIFY_CSS:=0 LUCI_MINIFY_JS:=0 diff --git a/luci-app-passwall2/Makefile b/luci-app-passwall2/Makefile index 1a8b5cca..c57ddef0 100644 --- a/luci-app-passwall2/Makefile +++ b/luci-app-passwall2/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:=luci-app-passwall2 PKG_VERSION:=26.9.9 -PKG_RELEASE:=115 +PKG_RELEASE:=116 PKG_PO_VERSION:=$(PKG_VERSION) PKG_CONFIG_DEPENDS:= \ diff --git a/luci-app-passwall2/luasrc/model/cbi/passwall2/client/acl_config.lua b/luci-app-passwall2/luasrc/model/cbi/passwall2/client/acl_config.lua index 8ffd788b..9493af6e 100644 --- a/luci-app-passwall2/luasrc/model/cbi/passwall2/client/acl_config.lua +++ b/luci-app-passwall2/luasrc/model/cbi/passwall2/client/acl_config.lua @@ -160,14 +160,10 @@ o:depends("mode", "1") o:depends("mode", "2") o.validate = port_validate -o = s:taboption("Main", DummyValue, "_show_tcp_redir", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_show_tcp_redir") o:depends({ tcp_no_redir_ports = "1:65535", ['!reverse'] = true }) -o = s:taboption("Main", DummyValue, "_show_udp_redir", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_show_udp_redir") o:depends({ udp_no_redir_ports = "1:65535", ['!reverse'] = true }) o = s:taboption("Proxy", Value, "tcp_redir_ports", translate("TCP Redir Ports")) @@ -195,15 +191,11 @@ end o:depends("mode", "1") o:depends("mode", "2") -o = s:taboption("Main", DummyValue, "_no_proxy", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_no_proxy") o:depends("mode", "0") o:depends({ tcp_no_redir_ports = "1:65535", udp_no_redir_ports = "1:65535" }) -o = s:taboption("Main", DummyValue, "_show_node_option", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_show_node_option") o:depends({ mode = "1", _no_proxy = "" }) o = s:taboption("Main", ListValue, "node", "" .. translate("Node") .. "") @@ -218,24 +210,17 @@ if node_value then end current_node = current_node_id and m:get(current_node_id) or {} -o = s:taboption("Main", DummyValue, "node_save_before", "") -o.template = m:template_path("/cbi/hidevalue") +o = s:taboption("Main", HideValue, "node_save_before") o.value = current_node[".name"] o.cbid = function(self, section) return "node_save_before" end -o = s:taboption("Main", DummyValue, "_node", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_node") o:depends({ node = "", ['!reverse'] = true }) -o = s:taboption("Main", DummyValue, "_is_singbox", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_is_singbox") o:depends("_hide", "1") -o = s:taboption("Main", DummyValue, "_is_xray", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_is_xray") o:depends("_hide", "1") o = s:taboption("Log", Flag, "log", translate("Enable Node Log")) @@ -267,9 +252,7 @@ o.cfgvalue = function(t, n) end o:depends("log", "1") -o = s:taboption("DNS", DummyValue, "_show_dns_option", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("DNS", HideValue, "_show_dns_option") o:depends({ mode = "1", _node = "1" }) o = s:taboption("DNS", ListValue, "direct_dns_query_strategy", translate("Direct Query Strategy")) diff --git a/luci-app-passwall2/luasrc/model/cbi/passwall2/client/global.lua b/luci-app-passwall2/luasrc/model/cbi/passwall2/client/global.lua index 7628e25f..c2fd0bab 100644 --- a/luci-app-passwall2/luasrc/model/cbi/passwall2/client/global.lua +++ b/luci-app-passwall2/luasrc/model/cbi/passwall2/client/global.lua @@ -85,14 +85,10 @@ o.template = m:template_path("/cbi/nodes_listvalue") o:value("", translate("Close")) o.group = {""} -o = s:taboption("Main", DummyValue, "_node", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_node") o:depends({ node = "", ['!reverse'] = true }) -o = s:taboption("Main", DummyValue, "_is_singbox", "") -o.template = m:template_path("/cbi/hidevalue") -o.value = "1" +o = s:taboption("Main", HideValue, "_is_singbox") o:depends("_hide", "1") current_node_id = m:get(s.section, "node") @@ -102,8 +98,7 @@ if node_value then end current_node = current_node_id and m:get(current_node_id) or {} -o = s:taboption("Main", DummyValue, "node_save_before", "") -o.template = m:template_path("/cbi/hidevalue") +o = s:taboption("Main", HideValue, "node_save_before") o.value = current_node[".name"] o.cbid = function(self, section) return "node_save_before" end diff --git a/luci-app-passwall2/luasrc/passwall2/api.lua b/luci-app-passwall2/luasrc/passwall2/api.lua index 89554bd7..8828ec02 100644 --- a/luci-app-passwall2/luasrc/passwall2/api.lua +++ b/luci-app-passwall2/luasrc/passwall2/api.lua @@ -1537,11 +1537,99 @@ function set_default_cbi() return cbi.AbstractValue.write(self, section, new_val) end end + if true then + --HideValue + local HideValue = util.class(cbi.DummyValue) + function HideValue.__init__(self, ...) + cbi.DummyValue.__init__(self, ...) + self.template = self.map:template_path("/cbi/hidevalue") + self.value = "1" + end + cbi.HideValue = HideValue + end +end + +function set_type_cbi(s) + local cbi = require "luci.cbi" + local s1 = s.parent + function s.option(s_self, class, option, ...) + local obj = class(s_self.map, s_self, option, ...) + obj.config_option = option + obj.option_prefix = s_self.option_prefix + obj.option = s_self.option_prefix .. option + obj.cfgvalue = function(self, section) + return self.map:get(section, self.config_option) + end + obj.write = function(self, section, value) + if s1.fields["type"]:formvalue(s_self.section) == s_self.type_name then + local new_val = value + if util.instanceof(self, cbi.DynamicList) then + local new_t = {} + if type(value) == "table" then + new_t = table_remove_duplicates(value) + else + new_t = { value } + end + if self.cast == "string" then + new_val = table.concat(new_t, " ") + else + new_val = new_t + end + end + self.map:set(section, self.config_option, new_val) + end + end + obj.remove = function(self, section) + if s1.fields["type"]:formvalue(s_self.section) == s_self.type_name then + self.map:del(section, self.config_option) + end + end + obj.deplist2json = function(self, section, deplist) + local deps, i, d = { } + if type(self.deps) == "table" then + if not next(self.deps) then + self:depends({ type = s.type_name }) + end + local list = deplist or self.deps + for i, d in ipairs(list) do + if s.type_name and not d["type"] then + d["type"] = s.type_name + end + local a, k, v = { } + for k, v in pairs(d) do + if k:find("!", 1, true) then + a[k] = v + elseif k:find("^", 1, true) then + a[k:sub(2)] = v + elseif k:find(".", 1, true) then + a['cbid%s' % k] = v + elseif s_self.fields[k] then + a['cbid.%s.%s.%s' %{ self.config, section, s_self.fields[k].option }] = v + else + a['cbid.%s.%s.%s' %{ self.config, section, k }] = v + end + end + deps[#deps+1] = a + end + end + return util.serialize_json(deps) + end + s_self:append(obj) + s_self.fields[option] = obj + return obj + end +end + +function type_cbi_section(s, s2) + for i, v in ipairs(s2.children) do + local o = s2.children[i] + s:append(o) + s.fields[o.option] = o + end end function return_map(map) local cbi = require "luci.cbi" - local api = require "luci.passwall2.api" if true then -- header local header = cbi.Template(appname .. "/cbi/header") @@ -1557,91 +1645,6 @@ function return_map(map) return map end -function set_type_cbi(s) - local cbi = require "luci.cbi" - local s1 = s.parent - function s.option(self, class, option, ...) - local obj = class(self.map, self, option, ...) - obj.config_option = option - obj.option_prefix = self.option_prefix - obj.option = self.option_prefix .. option - obj.cfgvalue = function(o_self, section) - if o_self.rewrite_option then - return o_self.map:get(section, o_self.rewrite_option) - else - return o_self.map:get(section, o_self.config_option) - end - end - obj.write = function(o_self, section, value) - if s1.fields["type"]:formvalue(self.section) == self.type_name then - local new_val = value - if util.instanceof(o_self, cbi.DynamicList) then - local new_t = {} - if type(value) == "table" then - new_t = table_remove_duplicates(value) - else - new_t = { value } - end - if o_self.cast == "string" then - new_val = table.concat(new_t, " ") - else - new_val = new_t - end - end - if o_self.rewrite_option then - o_self.map:set(section, o_self.rewrite_option, new_val) - else - o_self.map:set(section, o_self.config_option, new_val) - end - end - end - obj.remove = function(o_self, section) - if s1.fields["type"]:formvalue(self.section) == self.type_name then - if o_self.rewrite_option then - o_self.map:del(section, o_self.rewrite_option) - else - o_self.map:del(section, o_self.config_option) - end - end - end - obj.depends = function(o_self, field, value) - local deps - if type(field) == "string" then - deps = {} - deps[field] = value - else - deps = field - end - local new_deps = {} - for k, v in pairs(deps) do - local n_k = k - if self.fields[k] then - n_k = self.fields[k].option - end - new_deps[n_k] = v - end - new_deps["type"] = self.type_name - if next(new_deps) then - table.insert(o_self.deps, new_deps) - end - end - self:append(obj) - self.fields[option] = obj - return obj - end -end - -function type_cbi_section(s, s2) - for i, v in ipairs(s2.children) do - local o = s2.children[i] - if #o.deps == 0 then - o:depends({ type = s2.type_name }) - end - s:append(o) - s.fields[o.option] = o - end -end - function format_go_time(input, default) input = input and trim(input) local N = 0 diff --git a/luci-lib-linkeaseauth/Makefile b/luci-lib-linkeaseauth/Makefile index 9fa81e64..2b00a222 100644 --- a/luci-lib-linkeaseauth/Makefile +++ b/luci-lib-linkeaseauth/Makefile @@ -4,10 +4,9 @@ include $(TOPDIR)/rules.mk LUCI_TITLE:=LuCI shared OpenWrt auth bridge for LinkEase apps LUCI_PKGARCH:=all -PKG_PROVIDES:=luci-lib-openwrtauth PKG_VERSION:=1.0.1 -PKG_RELEASE:=3 +PKG_RELEASE:=4 include $(TOPDIR)/feeds/luci/luci.mk diff --git a/luci-nginxer/Makefile b/luci-nginxer/Makefile index 9a7fa935..21f57b55 100644 --- a/luci-nginxer/Makefile +++ b/luci-nginxer/Makefile @@ -8,13 +8,13 @@ include $(TOPDIR)/rules.mk LUCI_TITLE:=Nginxer LUCI_DESCRIPTION:=Standard OpenWrt set including full admin with ppp support and the default Bootstrap theme -PKG_VERSION:=0.0.2 -PKG_RELEASE:=11 +PKG_VERSION:=0.0.1 +PKG_RELEASE:=12 LUCI_DEPENDS:=+luci-nginx define Package/luci-nginxer/postrm #!/bin/sh -/etc/init.d/uhttpd enable +/etc/init.d/uhttpd enabled /etc/init.d/uhttpd start exit 0 endef diff --git a/luci-nginxer/root/etc/uci-defaults/50_luci-nginxer b/luci-nginxer/root/etc/uci-defaults/50_luci-nginxer index 18e28cfd..9d01f398 100644 --- a/luci-nginxer/root/etc/uci-defaults/50_luci-nginxer +++ b/luci-nginxer/root/etc/uci-defaults/50_luci-nginxer @@ -8,11 +8,7 @@ if [ "$nginxer" != 1 ]; then uci set nginx._redirect2ssl.access_log='off; # logd openwrt' uci set nginx.global.nginxer='1' uci commit nginx - - # fix firmware upload failed - sed -i 's/client_max_body_size 128M;/client_max_body_size 256M;/g' /etc/nginx/uci.conf.template - # /etc/init.d/uhttpd running || /etc/init.d/uhttpd disable /etc/init.d/nginx reload fi -exit 0 +exit 0 \ No newline at end of file diff --git a/luci-theme-footstrap/Makefile b/luci-theme-footstrap/Makefile index 5e66cc09..24f08647 100644 --- a/luci-theme-footstrap/Makefile +++ b/luci-theme-footstrap/Makefile @@ -17,7 +17,7 @@ LUCI_NAME:=luci-theme-footstrap FOOTSTRAP_VERSION?= ifneq ($(FOOTSTRAP_VERSION),) PKG_VERSION:=$(FOOTSTRAP_VERSION) -PKG_RELEASE:=64 +PKG_RELEASE:=65 endif LUCI_TITLE:=Footstrap Theme diff --git a/luci-theme-footstrap/htdocs/luci-static/resources/fs-fit.js b/luci-theme-footstrap/htdocs/luci-static/resources/fs-fit.js index 8dac07a0..ae11e3dc 100644 --- a/luci-theme-footstrap/htdocs/luci-static/resources/fs-fit.js +++ b/luci-theme-footstrap/htdocs/luci-static/resources/fs-fit.js @@ -68,14 +68,18 @@ function fittersEnabled() { /* One path for everything that may run now: the mutation observer, the coalesced re-fit and a pass * put off during a scroll all come through here, so the order — work, then the floor, then the * reference — is stated once. The correction is not this function's: observeContent() takes its - * reference before calling here and applies the offset afterwards. */ -function run() { + * reference before calling here and applies the offset afterwards. + * + * `records`, passed ONLY by the childList observer's own callback (below), is what lets + * `holdFloor()` skip a box nothing touched (task floorchurn) — every other caller leaves it + * undefined and gets the unscoped, every-box sweep, unchanged. */ +function run(records) { if (!fittersEnabled()) return; runAll(_fitters, 'fitter'); /* make the document whole again before anything lays it out, then take the position the next * mutation is measured against — unless a correction is already on its way, which would make * this reference the drifted one */ - holdFloor(); + holdFloor(records); if (!_anchorPending) rememberRest(); } @@ -141,8 +145,32 @@ const FLOORED = '[data-fs-floor]'; * * The climb is the ONE part of the 0.14.4 floor kept: this pass still clears and re-measures, so a * box that cannot hold anything up measures 0 with its floor off and gets none — which is why the - * collapsed tab pane of issue #41 cannot come back with it. */ -function holdFloor() { + * collapsed tab pane of issue #41 cannot come back with it. + * + * NOT EVERY BOX EVERY TIME — task floorchurn. Instrumented across 25s of real polling, three + * engines, two stands: 25 calls (5 per tick) times 29 candidate boxes is 725 clears and 625 writes, + * of which 610 put back the number already standing — only 15 boxes actually changed + * (`../tmp/task-floorsuppress/`). A box nobody has mutated cannot have a different height from the + * one this function measured it at last time: nothing else changes what `offsetHeight` answers here + * except a DOM mutation inside it (caught below) or a WIDTH change (a different codepath entirely — + * `onResize()` -> `schedule()` -> `run()` with no `records`, which still sweeps every box, since a + * reflow from a width change is invisible to a childList observer). So `records` — passed only by + * observeContent()'s own MutationObserver callback, `undefined` everywhere else in this file — + * narrows the clear/measure/write step to the boxes at least one record's `target` actually touched, + * either direction (`target` may be the box itself, a descendant the mutation changed, or an + * ANCESTOR of a box that just appeared as a fresh child of it — a plain `box.contains(target)` alone + * misses that last shape, since a box cannot contain the parent it was just inserted into). + * + * The climb itself — which boxes exist, and whether each one currently wears `data-fs-floor` — is + * still computed in full every call: cheap (`querySelectorAll` plus `getComputedStyle`, no forced + * layout) and it is what lets an untouched box be correctly recognised as untouched. What is skipped + * is only the clear-and-remeasure, the part that forces a layout per box. A box this call finds + * "not dirty" is left exactly as it was — for the ONE call that matters for correctness, the one + * `observeContent()`'s own callback reads `r.target`'s floor back from immediately after to compute + * `grew`/`floorShrink` (task blindref, task wkrefill), `r.target` already carries `data-fs-floor` + * and IS one of the mutation's own targets, so it is never excluded — this cannot silently swallow + * the shrink those mechanisms depend on seeing. */ +function holdFloor(records) { if (scrolling()) return; const host = document.getElementById('view'); if (!host) return; /* the login page has no view */ @@ -158,9 +186,18 @@ function holdFloor() { boxes.push(box); }); host.querySelectorAll(FLOORED).forEach((box) => { if (boxes.indexOf(box) === -1) boxes.push(box); }); - boxes.forEach((box) => { box.style.minHeight = ''; }); - boxes.forEach((box) => hs.push(box.offsetHeight)); - boxes.forEach((box, i) => { + + let dirty = boxes; + if (records && records.length) { + const targets = []; + for (const r of records) if (r.target && targets.indexOf(r.target) === -1) targets.push(r.target); + dirty = boxes.filter((box) => targets.some((t) => box.contains(t) || t.contains(box))); + } + if (!dirty.length) return; + + dirty.forEach((box) => { box.style.minHeight = ''; }); + dirty.forEach((box) => hs.push(box.offsetHeight)); + dirty.forEach((box, i) => { if (hs[i] > 0) { box.style.minHeight = hs[i] + 'px'; box.setAttribute('data-fs-floor', ''); } else box.removeAttribute('data-fs-floor'); }); @@ -1151,7 +1188,7 @@ function observeContent() { * any tick's `holdFloor()` actually runs, for the identical reason. */ const wasScrolling = scrolling(); if (r && before && wasScrolling) _deferredFloor = r.target; - run(); + run(records); if (!wasScrolling) _deferredFloor = null; const floorShrink = (r && before) ? Math.max(0, before - (parseFloat(r.target.style.minHeight) || 0)) : 0; if (trustEngine) lateDrift(settled, grew, floorShrink); @@ -1173,7 +1210,13 @@ function observeContent() { * {childList, subtree} registration above wherever body IS the content host. Merging them the * other way is worse — `subtree: true` plus an attribute filter wakes `run()` on every class * change in the document, and the poll rewrites row classes on every tick. */ - _moFlag = new MutationObserver(run); + /* wrapped, not passed bare: `run(records)` above means a MutationObserver callback handed to it + * directly would forward ITS OWN records as the dirty scope, and this observer's targets are + * `document.body`'s class attribute — never a box `holdFloor()` tracks — which would read as + * "nothing here is dirty" and skip the very sweep this observer exists to force (a dialog just + * became visible, or a poll rewrote a row's class). Call with none, and `holdFloor()` sweeps + * every box, as it always has for this trigger. */ + _moFlag = new MutationObserver(() => run()); _moFlag.observe(document.body, { attributes: true, attributeFilter: [ 'class' ] }); /* A TAB SWITCH — OR A DISCLOSURE CLOSING, OR A depends() ROW HIDING — MUTATES NO NODE. ui.tabs diff --git a/luci-theme-footstrap/update-po.sh b/luci-theme-footstrap/update-po.sh index 1ad85e83..834a263a 100755 --- a/luci-theme-footstrap/update-po.sh +++ b/luci-theme-footstrap/update-po.sh @@ -87,8 +87,10 @@ if [ "$CHECK" = 1 ]; then fi rc=0 + n=0 for po in po/*/*.po; do [ -e "$po" ] || continue + n=$((n + 1)) # an empty msgstr means the string renders in English for that language missing="$(msgfmt --statistics -o /dev/null "$po" 2>&1 | grep -o '[0-9]* untranslated' || true)" if [ -n "$missing" ]; then @@ -97,7 +99,15 @@ if [ "$CHECK" = 1 ]; then fi msgfmt --check -o /dev/null "$po" || rc=1 done - [ "$rc" = 0 ] && echo "i18n: .pot current, every string translated" + # A tree with no po/*/*.po at all walks zero catalogues, sets rc=0 (nothing in the loop ever ran + # to set it otherwise) and printed "every string translated" — true of the empty set the same way + # it is true of vacuously anything, and indistinguishable in the output from a real, fully + # translated build. n=0 is the one case the loop cannot tell apart from success on its own. + [ "$n" -gt 0 ] || { + echo "update-po: no po/*/*.po found — nothing was checked, not everything is translated" >&2 + exit 1 + } + [ "$rc" = 0 ] && echo "i18n: .pot current, every string translated ($n catalogue(s))" exit "$rc" fi