qBitrr2 5.7.1__py3-none-any.whl → 5.8.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- qBitrr/arss.py +25 -141
- qBitrr/bundled_data.py +2 -2
- qBitrr/database.py +79 -0
- qBitrr/main.py +14 -8
- qBitrr/search_activity_store.py +9 -39
- qBitrr/static/assets/ConfigView.js +4 -4
- qBitrr/static/assets/ConfigView.js.map +1 -1
- qBitrr/static/assets/LogsView.js +19 -19
- qBitrr/static/assets/LogsView.js.map +1 -1
- qBitrr/tables.py +11 -0
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/METADATA +19 -1
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/RECORD +16 -15
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/WHEEL +1 -1
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/entry_points.txt +0 -0
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/licenses/LICENSE +0 -0
- {qbitrr2-5.7.1.dist-info → qbitrr2-5.8.0.dist-info}/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import{u as Et,f as nr,p as sr,j as n,I,q as $e,t as ir,C as Xe,R as It,i as ar}from"./app.js";import{r as _}from"./table.js";import{g as or}from"./vendor.js";import{S as Me}from"./react-select.esm.js";var Ct=Symbol.for("immer-nothing"),lt=Symbol.for("immer-draftable"),D=Symbol.for("immer-state");function $(e,...t){throw new Error(`[Immer] minified error nr: ${e}. Full error at: https://bit.ly/3cXEKWf`)}var q=Object,re=q.getPrototypeOf,ye="constructor",we="prototype",We="configurable",ge="enumerable",me="writable",oe="value",H=e=>!!e&&!!e[D];function G(e){return e?Pt(e)||Ee(e)||!!e[lt]||!!e[ye]?.[lt]||Ie(e)||Ce(e):!1}var lr=q[we][ye].toString(),ct=new WeakMap;function Pt(e){if(!e||!Je(e))return!1;const t=re(e);if(t===null||t===q[we])return!0;const r=q.hasOwnProperty.call(t,ye)&&t[ye];if(r===Object)return!0;if(!te(r))return!1;let s=ct.get(r);return s===void 0&&(s=Function.toString.call(r),ct.set(r,s)),s===lr}function Ne(e,t,r=!0){ue(e)===0?(r?Reflect.ownKeys(e):q.keys(e)).forEach(a=>{t(a,e[a],e)}):e.forEach((s,a)=>t(a,s,e))}function ue(e){const t=e[D];return t?t.type_:Ee(e)?1:Ie(e)?2:Ce(e)?3:0}var dt=(e,t,r=ue(e))=>r===2?e.has(t):q[we].hasOwnProperty.call(e,t),Ke=(e,t,r=ue(e))=>r===2?e.get(t):e[t],Se=(e,t,r,s=ue(e))=>{s===2?e.set(t,r):s===3?e.add(r):e[t]=r};function cr(e,t){return e===t?e!==0||1/e===1/t:e!==e&&t!==t}var Ee=Array.isArray,Ie=e=>e instanceof Map,Ce=e=>e instanceof Set,Je=e=>typeof e=="object",te=e=>typeof e=="function",De=e=>typeof e=="boolean";function dr(e){const t=+e;return Number.isInteger(t)&&String(t)===e}var z=e=>e.copy_||e.base_,Ze=e=>e.modified_?e.copy_:e.base_;function ze(e,t){if(Ie(e))return new Map(e);if(Ce(e))return new Set(e);if(Ee(e))return Array[we].slice.call(e);const r=Pt(e);if(t===!0||t==="class_only"&&!r){const s=q.getOwnPropertyDescriptors(e);delete s[D];let a=Reflect.ownKeys(s);for(let i=0;i<a.length;i++){const o=a[i],c=s[o];c[me]===!1&&(c[me]=!0,c[We]=!0),(c.get||c.set)&&(s[o]={[We]:!0,[me]:!0,[ge]:c[ge],[oe]:e[o]})}return q.create(re(e),s)}else{const s=re(e);if(s!==null&&r)return{...e};const a=q.create(s);return q.assign(a,e)}}function et(e,t=!1){return Pe(e)||H(e)||!G(e)||(ue(e)>1&&q.defineProperties(e,{set:pe,add:pe,clear:pe,delete:pe}),q.freeze(e),t&&Ne(e,(r,s)=>{et(s,!0)},!1)),e}function ur(){$(2)}var pe={[oe]:ur};function Pe(e){return e===null||!Je(e)?!0:q.isFrozen(e)}var xe="MapSet",Ge="Patches",ut="ArrayMethods",At={};function X(e){const t=At[e];return t||$(0,e),t}var ft=e=>!!At[e],le,Ot=()=>le,fr=(e,t)=>({drafts_:[],parent_:e,immer_:t,canAutoFreeze_:!0,unfinalizedDrafts_:0,handledSet_:new Set,processedForPatches_:new Set,mapSetPlugin_:ft(xe)?X(xe):void 0,arrayMethodsPlugin_:ft(ut)?X(ut):void 0});function ht(e,t){t&&(e.patchPlugin_=X(Ge),e.patches_=[],e.inversePatches_=[],e.patchListener_=t)}function He(e){Ve(e),e.drafts_.forEach(hr),e.drafts_=null}function Ve(e){e===le&&(le=e.parent_)}var pt=e=>le=fr(le,e);function hr(e){const t=e[D];t.type_===0||t.type_===1?t.revoke_():t.revoked_=!0}function mt(e,t){t.unfinalizedDrafts_=t.drafts_.length;const r=t.drafts_[0];if(e!==void 0&&e!==r){r[D].modified_&&(He(t),$(4)),G(e)&&(e=bt(t,e));const{patchPlugin_:a}=t;a&&a.generateReplacementPatches_(r[D].base_,e,t)}else e=bt(t,r);return pr(t,e,!0),He(t),t.patches_&&t.patchListener_(t.patches_,t.inversePatches_),e!==Ct?e:void 0}function bt(e,t){if(Pe(t))return t;const r=t[D];if(!r)return ve(t,e.handledSet_,e);if(!Ae(r,e))return t;if(!r.modified_)return r.base_;if(!r.finalized_){const{callbacks_:s}=r;if(s)for(;s.length>0;)s.pop()(e);Mt(r,e)}return r.copy_}function pr(e,t,r=!1){!e.parent_&&e.immer_.autoFreeze_&&e.canAutoFreeze_&&et(t,r)}function Ft(e){e.finalized_=!0,e.scope_.unfinalizedDrafts_--}var Ae=(e,t)=>e.scope_===t,mr=[];function kt(e,t,r,s){const a=z(e),i=e.type_;if(s!==void 0&&Ke(a,s,i)===t){Se(a,s,r,i);return}if(!e.draftLocations_){const c=e.draftLocations_=new Map;Ne(a,(h,x)=>{if(H(x)){const p=c.get(x)||[];p.push(h),c.set(x,p)}})}const o=e.draftLocations_.get(t)??mr;for(const c of o)Se(a,c,r,i)}function br(e,t,r){e.callbacks_.push(function(a){const i=t;if(!i||!Ae(i,a))return;a.mapSetPlugin_?.fixSetContents(i);const o=Ze(i);kt(e,i.draft_??i,o,r),Mt(i,a)})}function Mt(e,t){if(e.modified_&&!e.finalized_&&(e.type_===3||e.type_===1&&e.allIndicesReassigned_||(e.assigned_?.size??0)>0)){const{patchPlugin_:s}=t;if(s){const a=s.getPath(e);a&&s.generatePatches_(e,a,t)}Ft(e)}}function yr(e,t,r){const{scope_:s}=e;if(H(r)){const a=r[D];Ae(a,s)&&a.callbacks_.push(function(){be(e);const o=Ze(a);kt(e,r,o,t)})}else G(r)&&e.callbacks_.push(function(){const i=z(e);e.type_===3?i.has(r)&&ve(r,s.handledSet_,s):Ke(i,t,e.type_)===r&&s.drafts_.length>1&&(e.assigned_.get(t)??!1)===!0&&e.copy_&&ve(Ke(e.copy_,t,e.type_),s.handledSet_,s)})}function ve(e,t,r){return!r.immer_.autoFreeze_&&r.unfinalizedDrafts_<1||H(e)||t.has(e)||!G(e)||Pe(e)||(t.add(e),Ne(e,(s,a)=>{if(H(a)){const i=a[D];if(Ae(i,r)){const o=Ze(i);Se(e,s,o,e.type_),Ft(i)}}else G(a)&&ve(a,t,r)})),e}function gr(e,t){const r=Ee(e),s={type_:r?1:0,scope_:t?t.scope_:Ot(),modified_:!1,finalized_:!1,assigned_:void 0,parent_:t,base_:e,draft_:null,copy_:null,revoke_:null,isManual_:!1,callbacks_:void 0};let a=s,i=_e;r&&(a=[s],i=ce);const{revoke:o,proxy:c}=Proxy.revocable(a,i);return s.draft_=c,s.revoke_=o,[c,s]}var _e={get(e,t){if(t===D)return e;let r=e.scope_.arrayMethodsPlugin_;const s=e.type_===1&&typeof t=="string";if(s&&r?.isArrayOperationMethod(t))return r.createMethodInterceptor(e,t);const a=z(e);if(!dt(a,t,e.type_))return Sr(e,a,t);const i=a[t];if(e.finalized_||!G(i)||s&&e.operationMethod&&r?.isMutatingArrayMethod(e.operationMethod)&&dr(t))return i;if(i===Ue(e.base_,t)){be(e);const o=e.type_===1?+t:t,c=Ye(e.scope_,i,e,o);return e.copy_[o]=c}return i},has(e,t){return t in z(e)},ownKeys(e){return Reflect.ownKeys(z(e))},set(e,t,r){const s=Dt(z(e),t);if(s?.set)return s.set.call(e.draft_,r),!0;if(!e.modified_){const a=Ue(z(e),t),i=a?.[D];if(i&&i.base_===r)return e.copy_[t]=r,e.assigned_.set(t,!1),!0;if(cr(r,a)&&(r!==void 0||dt(e.base_,t,e.type_)))return!0;be(e),Qe(e)}return e.copy_[t]===r&&(r!==void 0||t in e.copy_)||Number.isNaN(r)&&Number.isNaN(e.copy_[t])||(e.copy_[t]=r,e.assigned_.set(t,!0),yr(e,t,r)),!0},deleteProperty(e,t){return be(e),Ue(e.base_,t)!==void 0||t in e.base_?(e.assigned_.set(t,!1),Qe(e)):e.assigned_.delete(t),e.copy_&&delete e.copy_[t],!0},getOwnPropertyDescriptor(e,t){const r=z(e),s=Reflect.getOwnPropertyDescriptor(r,t);return s&&{[me]:!0,[We]:e.type_!==1||t!=="length",[ge]:s[ge],[oe]:r[t]}},defineProperty(){$(11)},getPrototypeOf(e){return re(e.base_)},setPrototypeOf(){$(12)}},ce={};for(let e in _e){let t=_e[e];ce[e]=function(){const r=arguments;return r[0]=r[0][0],t.apply(this,r)}}ce.deleteProperty=function(e,t){return ce.set.call(this,e,t,void 0)};ce.set=function(e,t,r){return _e.set.call(this,e[0],t,r,e[0])};function Ue(e,t){const r=e[D];return(r?z(r):e)[t]}function Sr(e,t,r){const s=Dt(t,r);return s?oe in s?s[oe]:s.get?.call(e.draft_):void 0}function Dt(e,t){if(!(t in e))return;let r=re(e);for(;r;){const s=Object.getOwnPropertyDescriptor(r,t);if(s)return s;r=re(r)}}function Qe(e){e.modified_||(e.modified_=!0,e.parent_&&Qe(e.parent_))}function be(e){e.copy_||(e.assigned_=new Map,e.copy_=ze(e.base_,e.scope_.immer_.useStrictShallowCopy_))}var xr=class{constructor(e){this.autoFreeze_=!0,this.useStrictShallowCopy_=!1,this.useStrictIteration_=!1,this.produce=(t,r,s)=>{if(te(t)&&!te(r)){const i=r;r=t;const o=this;return function(h=i,...x){return o.produce(h,p=>r.call(this,p,...x))}}te(r)||$(6),s!==void 0&&!te(s)&&$(7);let a;if(G(t)){const i=pt(this),o=Ye(i,t,void 0);let c=!0;try{a=r(o),c=!1}finally{c?He(i):Ve(i)}return ht(i,s),mt(a,i)}else if(!t||!Je(t)){if(a=r(t),a===void 0&&(a=t),a===Ct&&(a=void 0),this.autoFreeze_&&et(a,!0),s){const i=[],o=[];X(Ge).generateReplacementPatches_(t,a,{patches_:i,inversePatches_:o}),s(i,o)}return a}else $(1,t)},this.produceWithPatches=(t,r)=>{if(te(t))return(o,...c)=>this.produceWithPatches(o,h=>t(h,...c));let s,a;return[this.produce(t,r,(o,c)=>{s=o,a=c}),s,a]},De(e?.autoFreeze)&&this.setAutoFreeze(e.autoFreeze),De(e?.useStrictShallowCopy)&&this.setUseStrictShallowCopy(e.useStrictShallowCopy),De(e?.useStrictIteration)&&this.setUseStrictIteration(e.useStrictIteration)}createDraft(e){G(e)||$(8),H(e)&&(e=vr(e));const t=pt(this),r=Ye(t,e,void 0);return r[D].isManual_=!0,Ve(t),r}finishDraft(e,t){const r=e&&e[D];(!r||!r.isManual_)&&$(9);const{scope_:s}=r;return ht(s,t),mt(void 0,s)}setAutoFreeze(e){this.autoFreeze_=e}setUseStrictShallowCopy(e){this.useStrictShallowCopy_=e}setUseStrictIteration(e){this.useStrictIteration_=e}shouldUseStrictIteration(){return this.useStrictIteration_}applyPatches(e,t){let r;for(r=t.length-1;r>=0;r--){const a=t[r];if(a.path.length===0&&a.op==="replace"){e=a.value;break}}r>-1&&(t=t.slice(r+1));const s=X(Ge).applyPatches_;return H(e)?s(e,t):this.produce(e,a=>s(a,t))}};function Ye(e,t,r,s){const[a,i]=Ie(t)?X(xe).proxyMap_(t,r):Ce(t)?X(xe).proxySet_(t,r):gr(t,r);return(r?.scope_??Ot()).drafts_.push(a),i.callbacks_=r?.callbacks_??[],i.key_=s,r&&s!==void 0?br(r,i,s):i.callbacks_.push(function(h){h.mapSetPlugin_?.fixSetContents(i);const{patchPlugin_:x}=h;i.modified_&&x&&x.generatePatches_(i,[],h)}),a}function vr(e){return H(e)||$(10,e),Ut(e)}function Ut(e){if(!G(e)||Pe(e))return e;const t=e[D];let r,s=!0;if(t){if(!t.modified_)return t.base_;t.finalized_=!0,r=ze(e,t.scope_.immer_.useStrictShallowCopy_),s=t.scope_.immer_.shouldUseStrictIteration()}else r=ze(e,!0);return Ne(r,(a,i)=>{Se(r,a,Ut(i))},s),t&&(t.finalized_=!1),r}var _r=new xr,V=_r.produce,qe,yt;function Rr(){return yt||(yt=1,qe=function e(t,r){if(t===r)return!0;if(t&&r&&typeof t=="object"&&typeof r=="object"){if(t.constructor!==r.constructor)return!1;var s,a,i;if(Array.isArray(t)){if(s=t.length,s!=r.length)return!1;for(a=s;a--!==0;)if(!e(t[a],r[a]))return!1;return!0}if(t.constructor===RegExp)return t.source===r.source&&t.flags===r.flags;if(t.valueOf!==Object.prototype.valueOf)return t.valueOf()===r.valueOf();if(t.toString!==Object.prototype.toString)return t.toString()===r.toString();if(i=Object.keys(t),s=i.length,s!==Object.keys(r).length)return!1;for(a=s;a--!==0;)if(!Object.prototype.hasOwnProperty.call(r,i[a]))return!1;for(a=s;a--!==0;){var o=i[a];if(!e(t[o],r[o]))return!1}return!0}return t!==t&&r!==r}),qe}var jr=Rr();const gt=or(jr);var Tr=typeof global=="object"&&global&&global.Object===Object&&global,wr=typeof self=="object"&&self&&self.Object===Object&&self,tt=Tr||wr||Function("return this")(),ne=tt.Symbol,qt=Object.prototype,Nr=qt.hasOwnProperty,Er=qt.toString,ie=ne?ne.toStringTag:void 0;function Ir(e){var t=Nr.call(e,ie),r=e[ie];try{e[ie]=void 0;var s=!0}catch{}var a=Er.call(e);return s&&(t?e[ie]=r:delete e[ie]),a}var Cr=Object.prototype,Pr=Cr.toString;function Ar(e){return Pr.call(e)}var Or="[object Null]",Fr="[object Undefined]",St=ne?ne.toStringTag:void 0;function Lt(e){return e==null?e===void 0?Fr:Or:St&&St in Object(e)?Ir(e):Ar(e)}function kr(e){return e!=null&&typeof e=="object"}var Mr="[object Symbol]";function rt(e){return typeof e=="symbol"||kr(e)&&Lt(e)==Mr}function Dr(e,t){for(var r=-1,s=e==null?0:e.length,a=Array(s);++r<s;)a[r]=t(e[r],r,e);return a}var nt=Array.isArray,xt=ne?ne.prototype:void 0,vt=xt?xt.toString:void 0;function Bt(e){if(typeof e=="string")return e;if(nt(e))return Dr(e,Bt)+"";if(rt(e))return vt?vt.call(e):"";var t=e+"";return t=="0"&&1/e==-1/0?"-0":t}function Re(e){var t=typeof e;return e!=null&&(t=="object"||t=="function")}var Ur="[object AsyncFunction]",qr="[object Function]",Lr="[object GeneratorFunction]",Br="[object Proxy]";function $r(e){if(!Re(e))return!1;var t=Lt(e);return t==qr||t==Lr||t==Ur||t==Br}var Le=tt["__core-js_shared__"],_t=(function(){var e=/[^.]+$/.exec(Le&&Le.keys&&Le.keys.IE_PROTO||"");return e?"Symbol(src)_1."+e:""})();function Wr(e){return!!_t&&_t in e}var Kr=Function.prototype,zr=Kr.toString;function Gr(e){if(e!=null){try{return zr.call(e)}catch{}try{return e+""}catch{}}return""}var Hr=/[\\^$.*+?()[\]{}|]/g,Vr=/^\[object .+?Constructor\]$/,Qr=Function.prototype,Yr=Object.prototype,Xr=Qr.toString,Jr=Yr.hasOwnProperty,Zr=RegExp("^"+Xr.call(Jr).replace(Hr,"\\$&").replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g,"$1.*?")+"$");function en(e){if(!Re(e)||Wr(e))return!1;var t=$r(e)?Zr:Vr;return t.test(Gr(e))}function tn(e,t){return e?.[t]}function st(e,t){var r=tn(e,t);return en(r)?r:void 0}var Rt=(function(){try{var e=st(Object,"defineProperty");return e({},"",{}),e}catch{}})(),rn=9007199254740991,nn=/^(?:0|[1-9]\d*)$/;function sn(e,t){var r=typeof e;return t=t??rn,!!t&&(r=="number"||r!="symbol"&&nn.test(e))&&e>-1&&e%1==0&&e<t}function an(e,t,r){t=="__proto__"&&Rt?Rt(e,t,{configurable:!0,enumerable:!0,value:r,writable:!0}):e[t]=r}function $t(e,t){return e===t||e!==e&&t!==t}var on=Object.prototype,ln=on.hasOwnProperty;function cn(e,t,r){var s=e[t];(!(ln.call(e,t)&&$t(s,r))||r===void 0&&!(t in e))&&an(e,t,r)}var dn=/\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,un=/^\w*$/;function fn(e,t){if(nt(e))return!1;var r=typeof e;return r=="number"||r=="symbol"||r=="boolean"||e==null||rt(e)?!0:un.test(e)||!dn.test(e)||t!=null&&e in Object(t)}var de=st(Object,"create");function hn(){this.__data__=de?de(null):{},this.size=0}function pn(e){var t=this.has(e)&&delete this.__data__[e];return this.size-=t?1:0,t}var mn="__lodash_hash_undefined__",bn=Object.prototype,yn=bn.hasOwnProperty;function gn(e){var t=this.__data__;if(de){var r=t[e];return r===mn?void 0:r}return yn.call(t,e)?t[e]:void 0}var Sn=Object.prototype,xn=Sn.hasOwnProperty;function vn(e){var t=this.__data__;return de?t[e]!==void 0:xn.call(t,e)}var _n="__lodash_hash_undefined__";function Rn(e,t){var r=this.__data__;return this.size+=this.has(e)?0:1,r[e]=de&&t===void 0?_n:t,this}function J(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}J.prototype.clear=hn;J.prototype.delete=pn;J.prototype.get=gn;J.prototype.has=vn;J.prototype.set=Rn;function jn(){this.__data__=[],this.size=0}function Oe(e,t){for(var r=e.length;r--;)if($t(e[r][0],t))return r;return-1}var Tn=Array.prototype,wn=Tn.splice;function Nn(e){var t=this.__data__,r=Oe(t,e);if(r<0)return!1;var s=t.length-1;return r==s?t.pop():wn.call(t,r,1),--this.size,!0}function En(e){var t=this.__data__,r=Oe(t,e);return r<0?void 0:t[r][1]}function In(e){return Oe(this.__data__,e)>-1}function Cn(e,t){var r=this.__data__,s=Oe(r,e);return s<0?(++this.size,r.push([e,t])):r[s][1]=t,this}function se(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}se.prototype.clear=jn;se.prototype.delete=Nn;se.prototype.get=En;se.prototype.has=In;se.prototype.set=Cn;var Pn=st(tt,"Map");function An(){this.size=0,this.__data__={hash:new J,map:new(Pn||se),string:new J}}function On(e){var t=typeof e;return t=="string"||t=="number"||t=="symbol"||t=="boolean"?e!=="__proto__":e===null}function Fe(e,t){var r=e.__data__;return On(t)?r[typeof t=="string"?"string":"hash"]:r.map}function Fn(e){var t=Fe(this,e).delete(e);return this.size-=t?1:0,t}function kn(e){return Fe(this,e).get(e)}function Mn(e){return Fe(this,e).has(e)}function Dn(e,t){var r=Fe(this,e),s=r.size;return r.set(e,t),this.size+=r.size==s?0:1,this}function Z(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}Z.prototype.clear=An;Z.prototype.delete=Fn;Z.prototype.get=kn;Z.prototype.has=Mn;Z.prototype.set=Dn;var Un="Expected a function";function it(e,t){if(typeof e!="function"||t!=null&&typeof t!="function")throw new TypeError(Un);var r=function(){var s=arguments,a=t?t.apply(this,s):s[0],i=r.cache;if(i.has(a))return i.get(a);var o=e.apply(this,s);return r.cache=i.set(a,o)||i,o};return r.cache=new(it.Cache||Z),r}it.Cache=Z;var qn=500;function Ln(e){var t=it(e,function(s){return r.size===qn&&r.clear(),s}),r=t.cache;return t}var Bn=/[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g,$n=/\\(\\)?/g,Wn=Ln(function(e){var t=[];return e.charCodeAt(0)===46&&t.push(""),e.replace(Bn,function(r,s,a,i){t.push(a?i.replace($n,"$1"):s||r)}),t});function Kn(e){return e==null?"":Bt(e)}function Wt(e,t){return nt(e)?e:fn(e,t)?[e]:Wn(Kn(e))}function Kt(e){if(typeof e=="string"||rt(e))return e;var t=e+"";return t=="0"&&1/e==-1/0?"-0":t}function zn(e,t){t=Wt(t,e);for(var r=0,s=t.length;e!=null&&r<s;)e=e[Kt(t[r++])];return r&&r==s?e:void 0}function zt(e,t,r){var s=e==null?void 0:zn(e,t);return s===void 0?r:s}function Gn(e,t,r,s){if(!Re(e))return e;t=Wt(t,e);for(var a=-1,i=t.length,o=i-1,c=e;c!=null&&++a<i;){var h=Kt(t[a]),x=r;if(h==="__proto__"||h==="constructor"||h==="prototype")return e;if(a!=o){var p=c[h];x=void 0,x===void 0&&(x=Re(p)?p:sn(t[a+1])?[]:{})}cn(c,h,x),c=c[h]}return e}function Hn(e,t,r){return e==null?e:Gn(e,t,r)}const L={"Settings.ConfigVersion":"Internal schema version managed automatically by qBitrr for config migrations. DO NOT manually modify this value.","Settings.ConsoleLevel":"Level of logging; choose between CRITICAL, ERROR, WARNING, NOTICE, INFO, DEBUG, TRACE.","Settings.Logging":"Enable writing log output to files.","Settings.CompletedDownloadFolder":"Folder where completed downloads are stored. Replace backslashes with forward slashes.","Settings.FreeSpace":"Desired free space threshold (use K, M, G, T suffix). Set to -1 to disable the free space guard.","Settings.FreeSpaceFolder":"Path used when checking free space. Replace backslashes with forward slashes.","Settings.AutoPauseResume":"Automatically pause and resume torrents in response to the free space guard.","Settings.NoInternetSleepTimer":"Delay, in seconds, before retrying when no internet connectivity is detected.","Settings.LoopSleepTimer":"Delay, in seconds, between processing passes when monitoring torrents.","Settings.SearchLoopDelay":"Delay, in seconds, between media search requests.","Settings.FailedCategory":"Category that marks torrents as failed.","Settings.RecheckCategory":"Category that triggers recheck handling.","Settings.Tagless":"Enable tagless operation when categories are not used.","Settings.IgnoreTorrentsYoungerThan":"Ignore torrents younger than this many seconds when evaluating failures.","Settings.PingURLS":"Hostnames used to test for internet connectivity. They are pinged frequently.","Settings.FFprobeAutoUpdate":"Download and update the bundled ffprobe binary automatically.","Settings.AutoUpdateEnabled":"Enable the background worker that periodically checks for qBitrr updates.","Settings.AutoUpdateCron":"Cron expression describing when to check for updates (default weekly Sunday at 03:00).","Settings.AutoRestartProcesses":"Automatically restart worker processes that crash unexpectedly. Recommended to keep enabled for reliability.","Settings.MaxProcessRestarts":"Maximum number of times a worker process can be restarted within the restart window before auto-restart is disabled. Prevents infinite crash loops.","Settings.ProcessRestartWindow":"Time window in seconds for tracking restart attempts. If MaxProcessRestarts is exceeded within this window, auto-restart is disabled for that process.","Settings.ProcessRestartDelay":"Delay in seconds before restarting a crashed worker process. Gives time for transient issues to resolve.","WebUI.Host":"Interface address for the built-in WebUI. 0.0.0.0 binds on all interfaces.","WebUI.Port":"Port number for the built-in WebUI.","WebUI.Token":"Optional bearer token required by the WebUI/API. Leave empty to disable authentication.","WebUI.LiveArr":"Enable live updates for Arr views.","WebUI.GroupSonarr":"Group Sonarr views by series and seasons in collapsible sections.","WebUI.GroupLidarr":"Group Lidarr views by artist and albums in collapsible sections.","WebUI.Theme":"Choose the visual theme for the WebUI (light or dark).","qBit.Disabled":"Disable qBitrr's direct qBittorrent integration (headless mode for search-only setups).","qBit.Host":"qBittorrent WebUI host or IP address.","qBit.Port":"qBittorrent WebUI port.","qBit.UserName":"qBittorrent WebUI username.","qBit.Password":"qBittorrent WebUI password. Remove this if authentication is bypassed for the host.",Disabled:"Disable this qBittorrent instance (headless mode for search-only setups).",Host:"qBittorrent WebUI host or IP address.",Port:"qBittorrent WebUI port.",UserName:"qBittorrent WebUI username.",Password:"qBittorrent WebUI password. Remove this if authentication is bypassed for the host.","ARR.Managed":"Toggle whether this Servarr instance is actively managed by qBitrr.","ARR.URI":"Servarr URL, including protocol and port if needed (for example http://localhost:8989).","ARR.APIKey":"Servarr API key from Settings > General > Security.","ARR.Category":"qBittorrent category applied by the Servarr instance to its downloads.","ARR.ReSearch":"Re-run searches for failed torrents that qBitrr removes.","ARR.importMode":"Preferred import mode (Move, Copy, or Auto) when Servarr grabs completed files.","ARR.RssSyncTimer":"Interval, in minutes, between RSS sync requests (0 disables the task).","ARR.RefreshDownloadsTimer":"Interval, in minutes, between queue refresh requests (0 disables the task).","ARR.ArrErrorCodesToBlocklist":"List of Servarr error messages that should trigger blocklisting and cleanup.","EntrySearch.SearchMissing":"Search for missing media items.","EntrySearch.AlsoSearchSpecials":"Include season 0 specials in missing searches.","EntrySearch.Unmonitored":"Include unmonitored series or episodes in searches.","EntrySearch.SearchLimit":"Maximum number of concurrent search tasks (Servarr enforces its own limits).","EntrySearch.SearchByYear":"Order searches by the year the episode or movie first aired.","EntrySearch.SearchInReverse":"Reverse search order (search oldest to newest instead of newest to oldest).","EntrySearch.SearchRequestsEvery":"Delay, in seconds, between checking for new Overseerr/Ombi requests. After processing all pending requests, qBitrr waits this long before checking again. Default: 300 seconds (5 minutes).","EntrySearch.DoUpgradeSearch":"Search for improved releases even if a file already exists.","EntrySearch.QualityUnmetSearch":"Search again when the quality requirements were not met.","EntrySearch.CustomFormatUnmetSearch":"Search again when the minimum custom format score was not met.","EntrySearch.ForceMinimumCustomFormat":"Automatically remove torrents that do not meet the minimum custom format score.","EntrySearch.SearchAgainOnSearchCompletion":"Restart the search loop when the configured year range is exhausted.","EntrySearch.UseTempForMissing":"Switch to temporary profiles when searching for missing media.","EntrySearch.KeepTempProfile":"Do not revert to the main profile after using the temp profile.","EntrySearch.MainQualityProfile":"[DEPRECATED - Use QualityProfileMappings instead] Primary quality profile names, in the same order as the temporary profiles.","EntrySearch.TempQualityProfile":"[DEPRECATED - Use QualityProfileMappings instead] Temporary quality profile names, paired with the primary profiles.","EntrySearch.SearchBySeries":"Search by entire series instead of individual episodes when applicable.","EntrySearch.PrioritizeTodaysReleases":"Prioritise items released today (similar to RSS prioritisation).","EntrySearch.Ombi.SearchOmbiRequests":"Pull pending Ombi requests when SearchMissing is enabled.","EntrySearch.Ombi.OmbiURI":"Ombi server URL.","EntrySearch.Ombi.OmbiAPIKey":"Ombi API key.","EntrySearch.Ombi.ApprovedOnly":"Only process Ombi requests that are approved.","EntrySearch.Overseerr.SearchOverseerrRequests":"Pull Overseerr requests when SearchMissing is enabled.","EntrySearch.Overseerr.OverseerrURI":"Overseerr server URL.","EntrySearch.Overseerr.OverseerrAPIKey":"Overseerr API key.","EntrySearch.Overseerr.ApprovedOnly":"Only process Overseerr requests that are approved.","EntrySearch.Overseerr.Is4K":"Treat this Overseerr configuration as 4K specific.","Torrent.CaseSensitiveMatches":"When enabled, regex matches will respect case; otherwise they are case-insensitive.","Torrent.FolderExclusionRegex":"Regex patterns that exclude folders outright (full-name match).","Torrent.FileNameExclusionRegex":"Regex patterns that exclude individual files based on the file name.","Torrent.FileExtensionAllowlist":"Allowed file extensions (or regex) for downloads; leave empty to allow all.","Torrent.AutoDelete":"Automatically delete files that are not recognised as media.","Torrent.IgnoreTorrentsYoungerThan":"Ignore torrents younger than this many seconds for failure handling.","Torrent.MaximumETA":"Maximum allowed remaining ETA in seconds; values above this are considered stalled.","Torrent.MaximumDeletablePercentage":"Upper bound for completion percentage when deciding to delete a torrent.","Torrent.DoNotRemoveSlow":"Ignore slow torrents when pruning.","Torrent.StalledDelay":"Minutes to allow stalled torrents before taking action (-1 disables, 0 is infinite).","Torrent.ReSearchStalled":"Re-run searches for stalled torrents before or after removal depending on configuration.","Torrent.RemoveDeadTrackers":"Remove trackers flagged as dead.","Torrent.RemoveTrackerWithMessage":"Tracker status messages that should trigger tracker removal when RemoveDeadTrackers is enabled.","Torrent.SeedingMode.DownloadRateLimitPerTorrent":"Per-torrent download rate limit in bytes per second (-1 disables the limit).","Torrent.SeedingMode.UploadRateLimitPerTorrent":"Per-torrent upload rate limit in bytes per second (-1 disables the limit).","Torrent.SeedingMode.MaxUploadRatio":"Maximum allowed upload ratio (-1 disables the limit).","Torrent.SeedingMode.MaxSeedingTime":"Maximum seeding duration in seconds (-1 disables the limit).","Torrent.SeedingMode.RemoveTorrent":"Removal policy: -1 do not remove, 1 remove on ratio, 2 remove on time, 3 remove on ratio or time, 4 remove on ratio and time."};function jt(e){const t=e.join(".");if(L[t])return L[t];if(e.length>1){if(e[0]&&/^qBit(-.*)?$/i.test(e[0])){const c=["qBit",...e.slice(1)].join(".");if(L[c])return L[c]}const a=["ARR",...e.slice(1)].join(".");if(L[a])return L[a];const i=["EntrySearch",...e.slice(2)].join(".");if(e[1]==="EntrySearch"&&L[i])return L[i];const o=["Torrent",...e.slice(2)].join(".");if(e[1]==="Torrent"&&L[o])return L[o]}const r=e[e.length-1];return L[r]}const Vn="/static/assets/visibility.svg",je="/static/assets/plus.svg",ke="/static/assets/check-mark.svg",Te="/static/assets/trash.svg",at=/(rad|son|lid)arr/i,ot=/^qBit(-.*)?$/i,Be=()=>{const e=document.documentElement.getAttribute("data-theme")==="dark";return{control:t=>({...t,background:e?"#0f131a":"#ffffff",color:e?"#eaeef2":"#1d1d1f",borderColor:e?"#2a2f36":"#d2d2d7",minHeight:"38px",boxShadow:"none","&:hover":{borderColor:e?"#3a4149":"#b8b8bd"}}),menu:t=>({...t,background:e?"#0f131a":"#ffffff",borderColor:e?"#2a2f36":"#d2d2d7",border:`1px solid ${e?"#2a2f36":"#d2d2d7"}`}),option:(t,r)=>({...t,background:r.isFocused?e?"rgba(122, 162, 247, 0.15)":"rgba(0, 113, 227, 0.1)":e?"#0f131a":"#ffffff",color:e?"#eaeef2":"#1d1d1f","&:active":{background:e?"rgba(122, 162, 247, 0.25)":"rgba(0, 113, 227, 0.2)"}}),singleValue:t=>({...t,color:e?"#eaeef2":"#1d1d1f"}),input:t=>({...t,color:e?"#eaeef2":"#1d1d1f"}),placeholder:t=>({...t,color:e?"#9aa3ac":"#6e6e73"}),menuList:t=>({...t,padding:"4px"})}},Q=e=>String(e).split(",").map(t=>t.trim()).filter(Boolean),Y=e=>Array.isArray(e)?e.join(", "):String(e??""),Qn=["Move","Copy","Auto"],Yn=/(.+?[.!?])(\s|$)/;function Gt(e){if(!e)return;const t=e.trim();if(!t)return;const r=t.match(Yn),s=r?r[1]:t;return s.length>160?`${s.slice(0,157)}…`:s}const Ht=[{label:"Console Level",path:["Settings","ConsoleLevel"],type:"select",options:["CRITICAL","ERROR","WARNING","NOTICE","INFO","DEBUG","TRACE"],required:!0},{label:"Logging",path:["Settings","Logging"],type:"checkbox"},{label:"Completed Download Folder",path:["Settings","CompletedDownloadFolder"],type:"text",required:!0,validate:e=>{const t=String(e??"").trim();if(!t||t.toUpperCase()==="CHANGE_ME")return"Completed Download Folder must be set to a valid path."}},{label:"Free Space",path:["Settings","FreeSpace"],type:"text",required:!0,validate:e=>{const t=String(e??"").trim();if(!t)return"Free Space must be provided.";if(t!=="-1"&&!/^-?\d+(\.\d+)?[KMGTP]?$/i.test(t))return"Free Space must be -1 or a number optionally suffixed with K, M, G, T, or P."}},{label:"Free Space Folder",path:["Settings","FreeSpaceFolder"],type:"text",validate:(e,t)=>{const r=M(t.root,["Settings","FreeSpace"]);if(!(String(r??"").trim()!=="-1"))return;const a=String(e??"").trim();if(!a||a.toUpperCase()==="CHANGE_ME")return"Free Space Folder is required when Free Space monitoring is enabled."}},{label:"Auto Pause/Resume",path:["Settings","AutoPauseResume"],type:"checkbox"},{label:"No Internet Sleep (s)",path:["Settings","NoInternetSleepTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"No Internet Sleep must be a non-negative number."}},{label:"Loop Sleep (s)",path:["Settings","LoopSleepTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Loop Sleep must be a non-negative number."}},{label:"Search Loop Delay (s)",path:["Settings","SearchLoopDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Search Loop Delay must be a non-negative number."}},{label:"Failed Category",path:["Settings","FailedCategory"],type:"text"},{label:"Recheck Category",path:["Settings","RecheckCategory"],type:"text"},{label:"Tagless",path:["Settings","Tagless"],type:"checkbox"},{label:"Ignore Torrents Younger Than",path:["Settings","IgnoreTorrentsYoungerThan"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Ignore Torrents Younger Than must be a non-negative number."}},{label:"Ping URLs",path:["Settings","PingURLS"],type:"text",parse:Q,format:Y,placeholder:"one.one.one.one, dns.google.com"},{label:"FFprobe Auto Update",path:["Settings","FFprobeAutoUpdate"],type:"checkbox"},{label:"Auto Update Enabled",path:["Settings","AutoUpdateEnabled"],type:"checkbox"},{label:"Auto Update Cron",path:["Settings","AutoUpdateCron"],type:"text",placeholder:"0 3 * * 0",required:!0,validate:e=>{const r=String(e??"").trim().split(/\s+/).filter(Boolean);if(r.length<5||r.length>6)return"Auto Update Cron must contain 5 or 6 space-separated fields."}},{label:"Auto-Restart Processes",path:["Settings","AutoRestartProcesses"],type:"checkbox"},{label:"Max Process Restarts",path:["Settings","MaxProcessRestarts"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Max Process Restarts must be at least 1."}},{label:"Process Restart Window (s)",path:["Settings","ProcessRestartWindow"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Process Restart Window must be at least 1 second."}},{label:"Process Restart Delay (s)",path:["Settings","ProcessRestartDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Process Restart Delay must be a non-negative number."}}],Vt=[{label:"WebUI Host",path:["WebUI","Host"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"WebUI Host is required."}},{label:"WebUI Port",path:["WebUI","Port"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isInteger(t)||t<1||t>65535)return"WebUI Port must be between 1 and 65535."}},{label:"WebUI Token",path:["WebUI","Token"],type:"password",secure:!0,fullWidth:!0}],Qt=[{label:"Display Name",type:"text",placeholder:"qBit-seedbox",sectionName:!0},{label:"Disabled",path:["Disabled"],type:"checkbox"},{label:"Host",path:["Host"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"qBit Host is required."}},{label:"Port",path:["Port"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isInteger(t)||t<1||t>65535)return"qBit Port must be between 1 and 65535."}},{label:"UserName",path:["UserName"],type:"text"},{label:"Password",path:["Password"],type:"password",secure:!0}],Xn=[{label:"Display Name",type:"text",placeholder:"Sonarr-TV",sectionName:!0},{label:"Managed",path:["Managed"],type:"checkbox"},{label:"URI",path:["URI"],type:"text",placeholder:"http://host:port",required:!0,validate:(e,t)=>{const r=String(e??"").trim();if(M(t.section??{},["Managed"])&&(!r||r.toUpperCase()==="CHANGE_ME"))return"URI must be set to a valid URL when the instance is managed."}},{label:"API Key",path:["APIKey"],type:"password",secure:!0,required:!0,validate:(e,t)=>{const r=String(e??"").trim();if(M(t.section??{},["Managed"])&&(!r||r.toUpperCase()==="CHANGE_ME"))return"API Key must be provided when the instance is managed."}},{label:"Category",path:["Category"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"Category is required."}},{label:"Re-search",path:["ReSearch"],type:"checkbox"},{label:"Import Mode",path:["importMode"],type:"select",options:Qn,required:!0},{label:"RSS Sync Timer (min)",path:["RssSyncTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"RSS Sync Timer must be a non-negative number."}},{label:"Refresh Downloads Timer (min)",path:["RefreshDownloadsTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Refresh Downloads Timer must be a non-negative number."}},{label:"Arr Error Codes To Blocklist",path:["ArrErrorCodesToBlocklist"],type:"text",parse:Q,format:Y}],Jn=[{label:"Search Missing",path:["EntrySearch","SearchMissing"],type:"checkbox"},{label:"Also Search Specials",path:["EntrySearch","AlsoSearchSpecials"],type:"checkbox"},{label:"Unmonitored",path:["EntrySearch","Unmonitored"],type:"checkbox"},{label:"Do Upgrade Search",path:["EntrySearch","DoUpgradeSearch"],type:"checkbox"},{label:"Quality Unmet Search",path:["EntrySearch","QualityUnmetSearch"],type:"checkbox"},{label:"Custom Format Unmet Search",path:["EntrySearch","CustomFormatUnmetSearch"],type:"checkbox"},{label:"Force Minimum Custom Format",path:["EntrySearch","ForceMinimumCustomFormat"],type:"checkbox"},{label:"Search Limit",path:["EntrySearch","SearchLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Search Limit must be at least 1."}},{label:"Search By Year",path:["EntrySearch","SearchByYear"],type:"checkbox"},{label:"Search In Reverse",path:["EntrySearch","SearchInReverse"],type:"checkbox"},{label:"Search Requests Every (s)",path:["EntrySearch","SearchRequestsEvery"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Search Requests Every must be at least 1 second."}},{label:"Search Again On Completion",path:["EntrySearch","SearchAgainOnSearchCompletion"],type:"checkbox"},{label:"Use Temp Profile For Missing",path:["EntrySearch","UseTempForMissing"],type:"checkbox"},{label:"Keep Temp Profile",path:["EntrySearch","KeepTempProfile"],type:"checkbox"},{label:"Force Reset Temp Profiles",path:["EntrySearch","ForceResetTempProfiles"],type:"checkbox",description:"Reset all items using temp profiles to their original main profile on qBitrr startup"},{label:"Temp Profile Reset Timeout (Minutes)",path:["EntrySearch","TempProfileResetTimeoutMinutes"],type:"number",description:"Timeout in minutes after which items with temp profiles are automatically reset to main profile (0 = disabled)"},{label:"Profile Switch Retry Attempts",path:["EntrySearch","ProfileSwitchRetryAttempts"],type:"number",description:"Number of retry attempts for profile switch API calls (default: 3)"},{label:"Search By Series",path:["EntrySearch","SearchBySeries"],type:"select",options:["smart","true","false"],description:"smart = auto (series search for multiple episodes, episode search for single), true = always series search, false = always episode search",format:e=>typeof e=="boolean"?e?"true":"false":String(e||"smart"),parse:e=>{const t=String(e);return t==="true"||t==="false"?t:"smart"}},{label:"Prioritize Today's Releases",path:["EntrySearch","PrioritizeTodaysReleases"],type:"checkbox"}],Zn=[{label:"Search Ombi Requests",path:["EntrySearch","Ombi","SearchOmbiRequests"],type:"checkbox"},{label:"Ombi URI",path:["EntrySearch","Ombi","OmbiURI"],type:"text",placeholder:"http://host:port"},{label:"Ombi API Key",path:["EntrySearch","Ombi","OmbiAPIKey"],type:"password"},{label:"Approved Only",path:["EntrySearch","Ombi","ApprovedOnly"],type:"checkbox"},{label:"Is 4K Instance",path:["EntrySearch","Ombi","Is4K"],type:"checkbox"}],es=[{label:"Search Overseerr Requests",path:["EntrySearch","Overseerr","SearchOverseerrRequests"],type:"checkbox"},{label:"Overseerr URI",path:["EntrySearch","Overseerr","OverseerrURI"],type:"text",placeholder:"http://host:port"},{label:"Overseerr API Key",path:["EntrySearch","Overseerr","OverseerrAPIKey"],type:"password"},{label:"Approved Only",path:["EntrySearch","Overseerr","ApprovedOnly"],type:"checkbox"},{label:"Is 4K Instance",path:["EntrySearch","Overseerr","Is4K"],type:"checkbox"}],ts=[{label:"Case Sensitive Matches",path:["Torrent","CaseSensitiveMatches"],type:"checkbox"},{label:"Folder Exclusion Regex",path:["Torrent","FolderExclusionRegex"],type:"text",parse:Q,format:Y},{label:"File Name Exclusion Regex",path:["Torrent","FileNameExclusionRegex"],type:"text",parse:Q,format:Y},{label:"File Extension Allowlist",path:["Torrent","FileExtensionAllowlist"],type:"text",parse:Q,format:Y},{label:"Auto Delete",path:["Torrent","AutoDelete"],type:"checkbox"},{label:"Ignore Torrents Younger Than (s)",path:["Torrent","IgnoreTorrentsYoungerThan"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Ignore Torrents Younger Than must be a non-negative number."}},{label:"Maximum ETA (s)",path:["Torrent","MaximumETA"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Maximum ETA must be -1 or a non-negative number."}},{label:"Maximum Deletable Percentage",path:["Torrent","MaximumDeletablePercentage"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0||t>100)return"Maximum Deletable Percentage must be between 0 and 100."}},{label:"Do Not Remove Slow",path:["Torrent","DoNotRemoveSlow"],type:"checkbox"},{label:"Stalled Delay (min)",path:["Torrent","StalledDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Stalled Delay must be a non-negative number."}},{label:"Re-search Stalled",path:["Torrent","ReSearchStalled"],type:"checkbox"}],rs=[{label:"Download Rate Limit Per Torrent",path:["Torrent","SeedingMode","DownloadRateLimitPerTorrent"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Download Rate Limit must be -1 or greater."}},{label:"Upload Rate Limit Per Torrent",path:["Torrent","SeedingMode","UploadRateLimitPerTorrent"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Upload Rate Limit must be -1 or greater."}},{label:"Max Upload Ratio",path:["Torrent","SeedingMode","MaxUploadRatio"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Upload Ratio must be -1 or greater."}},{label:"Max Seeding Time (s)",path:["Torrent","SeedingMode","MaxSeedingTime"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Seeding Time must be -1 or greater."}},{label:"Remove Torrent (policy)",path:["Torrent","SeedingMode","RemoveTorrent"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t))return"Remove Torrent policy must be a number.";if(t!==-1&&![1,2,3,4].includes(t))return"Remove Torrent policy must be -1, 1, 2, 3, or 4."}},{label:"Remove Dead Trackers",path:["Torrent","SeedingMode","RemoveDeadTrackers"],type:"checkbox"},{label:"Remove Tracker Messages",path:["Torrent","SeedingMode","RemoveTrackerWithMessage"],type:"text",parse:Q,format:Y,fullWidth:!0}],ns=[{label:"Name",path:["Name"],type:"text",required:!0},{label:"URI",path:["URI"],type:"text",required:!0},{label:"Priority",path:["Priority"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Priority must be a non-negative number."}},{label:"Maximum ETA",path:["MaximumETA"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Maximum ETA must be -1 or a non-negative number."}},{label:"Download Rate Limit",path:["DownloadRateLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Download Rate Limit must be -1 or greater."}},{label:"Upload Rate Limit",path:["UploadRateLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Upload Rate Limit must be -1 or greater."}},{label:"Max Upload Ratio",path:["MaxUploadRatio"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Upload Ratio must be -1 or greater."}},{label:"Max Seeding Time",path:["MaxSeedingTime"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Seeding Time must be -1 or greater."}},{label:"Add Tracker If Missing",path:["AddTrackerIfMissing"],type:"checkbox"},{label:"Remove If Exists",path:["RemoveIfExists"],type:"checkbox"},{label:"Super Seed Mode",path:["SuperSeedMode"],type:"checkbox"},{label:"Add Tags",path:["AddTags"],type:"text",parse:Q,format:Y}];function Yt(e){const t=e.toLowerCase(),r=t.includes("sonarr"),s=t.includes("lidarr"),a=[...Xn],i=Jn.filter(d=>{if(!d.path)return!0;const w=d.path.join(".");return!(!r&&(w==="EntrySearch.AlsoSearchSpecials"||w==="EntrySearch.SearchBySeries"||w==="EntrySearch.PrioritizeTodaysReleases")||s&&w==="EntrySearch.SearchByYear")}),o=s?[]:[...Zn],c=s?[]:[...es],h=[...ts],x=[...rs],p=[...ns];return{generalFields:a,entryFields:i,entryOmbiFields:o,entryOverseerrFields:c,torrentFields:h,seedingFields:x,trackerFields:p}}function Tt(e){return e==null||typeof e=="string"&&e.trim()===""||Array.isArray(e)&&e.length===0}function ss(e,t){const r=e.label,s=e.required??(e.type==="number"||e.type==="select");switch(e.type){case"text":case"password":return s&&Tt(t)?`${r} is required.`:void 0;case"number":{if(t==null||t==="")return s?`${r} is required.`:void 0;const a=typeof t=="number"?t:Number(t);return Number.isFinite(a)?void 0:`${r} must be a valid number.`}case"checkbox":return t==null?s?`${r} is required.`:void 0:typeof t!="boolean"?`${r} must be true or false.`:void 0;case"select":return Tt(t)?`${r} is required.`:typeof t!="string"?`${r} must be selected.`:e.options&&!e.options.includes(t)?`${r} must be one of ${e.options.join(", ")}.`:void 0;default:return}}function K(e,t,r,s,a){if(r)for(const i of t){if(i.sectionName)continue;const o=i.path??[],c=o.length?M(r,o):void 0,h=[...s,...o],x=ss(i,c);if(x){e.push({path:h,message:x});continue}if(i.validate){const p=i.validate(c,a);p&&e.push({path:h,message:p})}}}function is(e){if(!e)return[];const t=[],r={root:e};K(t,Ht,e,[],r),K(t,Vt,e,[],r);for(const[s,a]of Object.entries(e))if(ot.test(s)&&a&&typeof a=="object"){const i=a;K(t,Qt,i,[s],{root:e,section:i,sectionKey:s})}else if(at.test(s)&&a&&typeof a=="object"){const i=a,o={root:e,section:i,sectionKey:s},c=Yt(s);K(t,c.generalFields,i,[s],o),K(t,c.entryFields,i,[s],o),K(t,c.entryOmbiFields,i,[s],o),K(t,c.entryOverseerrFields,i,[s],o),K(t,c.torrentFields,i,[s],o),K(t,c.seedingFields,i,[s],o)}return t}function M(e,t){if(e)return zt(e,t)}function as(e,t,r){Hn(e,t,r)}function ae(e,t=[]){const r={};for(const[s,a]of Object.entries(e)){const i=[...t,s];a&&typeof a=="object"&&!Array.isArray(a)?Object.assign(r,ae(a,i)):r[i.join(".")]=a}return r}function os(e){const t=e.toLowerCase(),r=t.includes("sonarr"),s=t.includes("radarr"),a=t.includes("lidarr"),i=s?["Not a preferred word upgrade for existing movie file(s)","Not an upgrade for existing movie file(s)","Unable to determine if file is a sample"]:a?["Not a preferred word upgrade for existing album file(s)","Not an upgrade for existing album file(s)","Unable to determine if file is a sample"]:["Not a preferred word upgrade for existing episode file(s)","Not an upgrade for existing episode file(s)","Unable to determine if file is a sample"],o={SearchMissing:!0,Unmonitored:!1,SearchLimit:5,SearchByYear:!0,SearchInReverse:!1,SearchRequestsEvery:300,DoUpgradeSearch:!1,QualityUnmetSearch:!1,CustomFormatUnmetSearch:!1,ForceMinimumCustomFormat:!1,SearchAgainOnSearchCompletion:!0,UseTempForMissing:!1,KeepTempProfile:!1,ForceResetTempProfiles:!1,TempProfileResetTimeoutMinutes:0,ProfileSwitchRetryAttempts:3,QualityProfileMappings:{}};return r&&(o.AlsoSearchSpecials=!1,o.SearchBySeries="smart",o.PrioritizeTodaysReleases=!0),o.Ombi={SearchOmbiRequests:!1,OmbiURI:"CHANGE_ME",OmbiAPIKey:"CHANGE_ME",ApprovedOnly:!0},o.Overseerr={SearchOverseerrRequests:!1,OverseerrURI:"CHANGE_ME",OverseerrAPIKey:"CHANGE_ME",ApprovedOnly:!0,Is4K:!1},{Managed:!0,URI:"CHANGE_ME",APIKey:"CHANGE_ME",Category:e,ReSearch:!0,importMode:"Auto",RssSyncTimer:5,RefreshDownloadsTimer:5,ArrErrorCodesToBlocklist:i,EntrySearch:o,Torrent:{CaseSensitiveMatches:!1,FolderExclusionRegex:["\\bextras?\\b","\\bfeaturettes?\\b","\\bsamples?\\b","\\bscreens?\\b","\\bnc(ed|op)?(\\\\d+)?\\b"],FileNameExclusionRegex:["\\bncop\\\\d+?\\b","\\bnced\\\\d+?\\b","\\bsample\\b","brarbg.com\\b","\\btrailer\\b","music video","comandotorrents.com"],FileExtensionAllowlist:a?[".mp3",".flac",".m4a",".aac",".ogg",".opus",".wav",".ape",".wma",".!qB",".parts",".log",".cue"]:[".mp4",".mkv",".sub",".ass",".srt",".!qB",".parts"],AutoDelete:!1,IgnoreTorrentsYoungerThan:600,MaximumETA:604800,MaximumDeletablePercentage:.99,DoNotRemoveSlow:!0,StalledDelay:15,ReSearchStalled:!1,RemoveDeadTrackers:!1,RemoveTrackerWithMessage:["skipping tracker announce (unreachable)","No such host is known","unsupported URL protocol","info hash is not authorized with this tracker"],SeedingMode:{DownloadRateLimitPerTorrent:-1,UploadRateLimitPerTorrent:-1,MaxUploadRatio:-1,MaxSeedingTime:-1,RemoveTorrent:-1}}}}function ys(e){const{onDirtyChange:t}=e??{},{push:r}=Et(),[s,a]=_.useState(null),[i,o]=_.useState(null),[c,h]=_.useState(!1),[x,p]=_.useState(!1),d=_.useCallback(async()=>{h(!0);try{const l=await nr();a(l),o(l?JSON.parse(JSON.stringify(l)):null)}catch(l){r(l instanceof Error?l.message:"Failed to load configuration","error")}finally{h(!1)}},[r]);_.useEffect(()=>{d()},[d]);const w=_.useCallback((l,u,f)=>{if(!i)return;const g=u.parse?.(f)??(u.type==="number"?Number(f)||0:u.type==="checkbox"?!!f:f);o(V(i,R=>{as(R,l,g)}))},[i]),v=_.useMemo(()=>i?Object.entries(i).filter(([l,u])=>at.test(l)&&u&&typeof u=="object"):[],[i]),N=_.useMemo(()=>i?Object.entries(i).filter(([l,u])=>ot.test(l)&&u&&typeof u=="object"):[],[i]),C=_.useMemo(()=>{const l=[],u=[...v].sort((O,W)=>O[0].localeCompare(W[0],void 0,{numeric:!0,sensitivity:"base"})),f=[],g=[],R=[],A=[];for(const O of u){const[W]=O,k=W.toLowerCase();k.startsWith("radarr")?f.push(O):k.startsWith("sonarr")?g.push(O):k.startsWith("lidarr")?R.push(O):A.push(O)}return l.push({label:"Radarr Instances",type:"radarr",items:f}),l.push({label:"Sonarr Instances",type:"sonarr",items:g}),l.push({label:"Lidarr Instances",type:"lidarr",items:R}),A.length&&l.push({label:"Other Instances",type:"other",items:A}),l},[v]),[j,T]=_.useState(null),[b,E]=_.useState(null),[S,m]=_.useState(!1),[y,P]=_.useState(!1),[F,U]=_.useState(!1);_.useEffect(()=>{if(!i||!s){U(!1);return}const l=ae(s),u=ae(i),f=new Set(["WebUI.LiveArr","WebUI.GroupSonarr","WebUI.GroupLidarr","WebUI.Theme"]);let g=!1;for(const[R,A]of Object.entries(u)){if(f.has(R))continue;const O=l[R];if(!gt(A,O)){g=!0;break}}if(!g){for(const R of Object.keys(l))if(!f.has(R)&&!(R in u)){g=!0;break}}U(g)},[i,s]),_.useEffect(()=>{t?.(F)},[F,t]),_.useEffect(()=>{if(!F)return;const l=u=>{u.preventDefault(),u.returnValue=""};return window.addEventListener("beforeunload",l),()=>{window.removeEventListener("beforeunload",l)}},[F]),_.useEffect(()=>()=>{t?.(!1)},[t]),_.useEffect(()=>{if(!!!(j||b||S||y))return;const u=R=>{R.key==="Escape"&&(T(null),E(null),m(!1),P(!1))};window.addEventListener("keydown",u);const{style:f}=document.body,g=f.overflow;return f.overflow="hidden",()=>{window.removeEventListener("keydown",u),f.overflow=g}},[j,b,S,y]),_.useEffect(()=>{j&&(v.some(([l])=>l===j)||T(null))},[j,v]);const fe=_.useCallback(l=>{if(!i)return;const u=l.charAt(0).toUpperCase()+l.slice(1);let f=1,g=`${u}-${f}`;for(;i[g];)f+=1,g=`${u}-${f}`;const R=os(l);R&&typeof R=="object"&&(R.Name=g),o(V(i,A=>{A[g]=R})),T(g)},[i]),Xt=_.useCallback(l=>{if(!i)return;const u=l.toLowerCase();!u.startsWith("radarr")&&!u.startsWith("sonarr")&&!u.startsWith("lidarr")||!window.confirm(`Delete ${l}? This action cannot be undone.`)||l in i&&(o(V(i,g=>{delete g[l]})),j===l&&T(null),r(`${l} removed`,"success"))},[i,j,r]),Jt=_.useCallback(()=>{if(!i)return;let l=1,u=`qBit-${l}`;for(;i[u];)l+=1,u=`qBit-${l}`;const f={Disabled:!1,Host:"localhost",Port:8080,UserName:"",Password:""};o(V(i,g=>{g[u]=f})),E(u)},[i]),Zt=_.useCallback(l=>{if(!i)return;if(l==="qBit"){r("Cannot delete the default qBit instance","error");return}window.confirm(`Delete ${l}? This action cannot be undone.`)&&l in i&&(o(V(i,f=>{delete f[l]})),b===l&&E(null),r(`${l} removed`,"success"))},[i,b,r]),er=_.useCallback((l,u)=>{if(!i)return;const f=u.trim();if(!(!f||f===l)){if(i[f]){r(`An instance named "${f}" already exists`,"error");return}o(V(i,g=>{const R=g[l];delete g[l],g[f]=R,R&&typeof R=="object"&&(R.Name=f)})),j===l&&T(f)}},[i,r,j]),tr=_.useCallback((l,u)=>{if(!i)return;const f=u.trim();if(!(!f||f===l)){if(l==="qBit"&&f!=="qBit"){r("Cannot rename the default qBit instance. Create a new instance instead.","error");return}if(i[f]){r(`An instance named "${f}" already exists`,"error");return}o(V(i,g=>{const R=g[l];delete g[l],g[f]=R})),b===l&&E(f)}},[i,r,b]),rr=_.useCallback(async()=>{if(i){p(!0);try{const l=is(i);if(l.length){const k=l.map(he=>`${he.path.join(".")}: ${he.message}`).join(`
|
|
2
|
-
`),ee=l.length===1?
|
|
3
|
-
${k}`;r(ee,"error"),p(!1);return}const u=ae(s??{}),f=ae(i),g={};for(const[k,ee]of Object.entries(f)){const he=u[k];gt(ee,he)||(g[k]=ee)}for(const k of Object.keys(u))k in f||(g[k]=null);if(Object.keys(g).length===0){r("No changes detected","info"),p(!1);return}const{configReloaded:R,reloadType:A,affectedInstances:O}=await sr({changes:g});let W="Configuration saved";if(A==="full"?W+=" • All instances reloaded":A==="multi_arr"&&O?.length?W+=` • Reloaded ${O.length} instances: ${O.join(", ")}`:A==="single_arr"&&O?.length?W+=` • Reloaded: ${O.join(", ")}`:A==="webui"?W+=" • WebUI restarting...":A==="frontend"&&(W+=" • Theme/display settings updated"),r(W,"success"),R&&"caches"in window)try{const k=await caches.keys();await Promise.all(k.map(ee=>caches.delete(ee)))}catch(k){console.warn("Failed to clear caches:",k)}await d()}catch(l){r(l instanceof Error?l.message:"Failed to update configuration","error")}finally{p(!1)}}},[i,s,d,r]);return c||!i?n.jsxs("section",{className:"card",children:[n.jsx("div",{className:"card-header",children:"Config"}),n.jsx("div",{className:"card-body",children:n.jsxs("div",{className:"loading",children:[n.jsx("span",{className:"spinner"})," Loading configuration…"]})})]}):n.jsxs(n.Fragment,{children:[n.jsxs("section",{className:"card",children:[n.jsx("div",{className:"card-header",children:"Config"}),n.jsxs("div",{className:"card-body config-layout",children:[n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsx("summary",{children:n.jsx("span",{children:"Core Configuration"})}),n.jsxs("div",{className:"config-grid",children:[n.jsx(wt,{title:"Settings",description:"Core application configuration",onConfigure:()=>m(!0)}),n.jsx(wt,{title:"Web Settings",description:"Web UI configuration",onConfigure:()=>P(!0)})]})]})}),n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsxs("summary",{children:[n.jsx("span",{children:"qBittorrent Instances"}),n.jsx("span",{className:"config-arr-group__count",children:N.length}),n.jsxs("button",{className:"btn small",type:"button",onClick:Jt,children:[n.jsx(I,{src:je}),"Add Instance"]})]}),n.jsx("div",{className:"config-arr-grid",children:N.map(([l,u])=>{const f=M(u,["Host"]),g=M(u,["Port"]),R=M(u,["Disabled"]),A=l==="qBit";return n.jsxs("div",{className:"card config-card config-arr-card",children:[n.jsxs("div",{className:"card-header",children:[l,A&&n.jsx("span",{style:{marginLeft:"8px",opacity:.6},children:"(Default)"})]}),n.jsxs("div",{className:"card-body",children:[n.jsxs("dl",{className:"config-arr-summary",children:[n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Status"}),n.jsx("dd",{children:R?"Disabled":"Enabled"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Host"}),n.jsx("dd",{children:f?`${String(f)}:${g??8080}`:"-"})]})]}),n.jsxs("div",{className:"config-arr-actions",children:[A?null:n.jsxs("button",{className:"btn danger",type:"button",onClick:()=>Zt(l),children:[n.jsx(I,{src:Te}),"Delete"]}),n.jsxs("button",{className:"btn primary",type:"button",onClick:()=>E(l),children:[n.jsx(I,{src:$e}),"Configure"]})]})]})]},l)})})]})}),C.length?n.jsx("div",{className:"config-arr-groups",children:C.map(l=>n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsxs("summary",{children:[n.jsx("span",{children:l.label}),n.jsx("span",{className:"config-arr-group__count",children:l.items.length}),(l.type==="radarr"||l.type==="sonarr"||l.type==="lidarr")&&n.jsxs("button",{className:"btn small",type:"button",onClick:()=>fe(l.type),children:[n.jsx(I,{src:je}),"Add Instance"]})]}),n.jsx("div",{className:"config-arr-grid",children:l.items.map(([u,f])=>{const g=M(f,["URI"]),R=M(f,["Category"]),A=M(f,["Managed"]),O=l.type==="radarr"||l.type==="sonarr"||l.type==="lidarr";return n.jsxs("div",{className:"card config-card config-arr-card",children:[n.jsx("div",{className:"card-header",children:u}),n.jsxs("div",{className:"card-body",children:[n.jsxs("dl",{className:"config-arr-summary",children:[n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Managed"}),n.jsx("dd",{children:A?"Enabled":"Disabled"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Category"}),n.jsx("dd",{children:R?String(R):"-"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"URI"}),n.jsx("dd",{className:"config-arr-summary__uri",children:g?String(g):"-"})]})]}),n.jsxs("div",{className:"config-arr-actions",children:[O?n.jsxs("button",{className:"btn danger",type:"button",onClick:()=>Xt(u),children:[n.jsx(I,{src:Te}),"Delete"]}):null,n.jsxs("button",{className:"btn primary",type:"button",onClick:()=>T(u),children:[n.jsx(I,{src:$e}),"Configure"]})]})]})]},u)})})]})},l.type))}):null,n.jsx("div",{className:"config-footer",children:n.jsxs("button",{className:"btn primary",onClick:()=>{rr()},disabled:x,children:[n.jsx(I,{src:ke}),"Save + Live Reload"]})})]})]}),j&&i?n.jsx(us,{keyName:j,state:i[j]??null,onChange:w,onRename:er,onClose:()=>T(null)}):null,S?n.jsx(Nt,{title:"Settings",fields:Ht,state:i,basePath:[],onChange:w,onClose:()=>m(!1)}):null,y?n.jsx(Nt,{title:"Web Settings",fields:Vt,state:i,basePath:[],onChange:w,onClose:()=>P(!1),showLiveSettings:!0}):null,b&&i?n.jsx(fs,{keyName:b,state:i[b]??null,onChange:w,onRename:tr,onClose:()=>E(null)}):null]})}function wt({title:e,description:t,onConfigure:r}){return n.jsxs("div",{className:"card config-card",children:[n.jsx("div",{className:"card-header",children:e}),n.jsxs("div",{className:"card-body config-summary-card",children:[n.jsx("p",{children:t}),n.jsx("div",{className:"config-arr-actions",children:n.jsxs("button",{className:"btn primary",type:"button",onClick:r,children:[n.jsx(I,{src:$e}),"Configure"]})})]})]})}function B({title:e,fields:t,state:r,basePath:s,onChange:a,onRenameSection:i,defaultOpen:o=!1,qualityProfiles:c=[],sectionKey:h}){const x=h??s[0]??"";if(e==="Quality Profile Mappings"){const d=M(r,["EntrySearch","QualityProfileMappings"])??{},w=Object.entries(d),v=!!(M(r,["URI"])&&M(r,["APIKey"])),N=c.length>0,C=()=>{const b={...d,"":""};a([...s,"EntrySearch","QualityProfileMappings"],{},b)},j=(b,E,S)=>{const m={...d};b!==E&&delete m[b],E.trim()&&(m[E.trim()]=S.trim()),a([...s,"EntrySearch","QualityProfileMappings"],{},m)},T=b=>{const E={...d};delete E[b],a([...s,"EntrySearch","QualityProfileMappings"],{},E)};return n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsxs("div",{className:"config-section__body",children:[n.jsx("div",{className:"field-description",style:{marginBottom:"1rem"},children:"Map main quality profile names to temporary profile names. Items will be downgraded to the temp profile when not found, then upgraded back to the main profile when available."}),v?N?n.jsxs(n.Fragment,{children:[n.jsx("div",{className:"profile-mappings-grid",children:w.map(([b,E],S)=>n.jsxs("div",{className:"profile-mapping-row",children:[n.jsxs("div",{className:"field",children:[n.jsx("label",{children:"Main Profile"}),n.jsx(Me,{options:c.map(m=>({value:m.name,label:m.name})),value:b?{value:b,label:b}:null,onChange:m=>j(b,m?.value||"",E),placeholder:"Select main profile...",isClearable:!0,styles:Be(),classNamePrefix:"react-select"})]}),n.jsxs("div",{className:"field",children:[n.jsx("label",{children:"Temp Profile"}),n.jsx(Me,{options:c.map(m=>({value:m.name,label:m.name})),value:E?{value:E,label:E}:null,onChange:m=>j(b,b,m?.value||""),placeholder:"Select temp profile...",isClearable:!0,styles:Be(),classNamePrefix:"react-select"})]}),n.jsx("button",{className:"btn ghost icon-only",type:"button",onClick:()=>T(b),title:"Delete mapping",children:n.jsx(I,{src:Te})})]},S))}),n.jsx("div",{className:"config-actions",children:n.jsxs("button",{className:"btn",type:"button",onClick:C,children:[n.jsx(I,{src:je}),"Add Profile Mapping"]})})]}):n.jsxs("div",{className:"alert info",children:['ℹ️ Click "Test Connection" above to load quality profiles from your ',x," instance"]}):n.jsx("div",{className:"alert warning",children:'⚠️ Please configure URI and API Key first, then click "Test Connection" to load quality profiles'})]})]})}if(e==="Trackers"){const d=M(r,["Torrent","Trackers"])??[],w=()=>{const N=[...d,{Url:"",RemoveIfExists:!1,SuperSeedMode:!1,AddTags:[]}];a([...s,"Torrent","Trackers"],{},N)},v=N=>{const C=[...d];C.splice(N,1),a([...s,"Torrent","Trackers"],{},C)};return n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsxs("div",{className:"config-section__body",children:[n.jsx("div",{className:"tracker-grid",children:d.map((N,C)=>n.jsx(ls,{fields:t,state:N,basePath:[...s,"Torrent","Trackers",String(C)],onChange:a,onDelete:()=>v(C)},C))}),n.jsx("div",{className:"config-actions",children:n.jsxs("button",{className:"btn",type:"button",onClick:w,children:[n.jsx(I,{src:je}),"Add Tracker"]})})]})]})}const p=t.map(d=>{if(d.sectionName){if(!x)return null;const y=jt([x]);let P;return x.startsWith("Radarr")?P="Radarr":x.startsWith("Sonarr")?P="Sonarr":x.startsWith("Lidarr")&&(P="Lidarr"),n.jsx(cs,{label:d.label,tooltip:y,currentName:x,placeholder:d.placeholder,expectedPrefix:P,onRename:F=>i?.(x,F)},`${x}.__name`)}const w=d.path??[],v=[...s,...w],N=v.join("."),C=v.length>0?M(r,v):void 0,j=d.format?.(C)??(d.type==="checkbox"?!!C:String(C??"")),T=jt(v),b=d.description??Gt(T)??(d.type==="checkbox"?`Enable or disable ${d.label}.`:`Set the ${d.label} value.`),S=s.length>0&&at.test(s[0]??"")&&(d.path?.[d.path.length-1]??"")==="APIKey",m=d.fullWidth?"field field--full-width":"field";if(d.secure)return n.jsx(ds,{label:d.label,tooltip:T,description:b,value:String(C??""),placeholder:d.placeholder,canRefresh:!S,onChange:y=>a(v,d,y)},N);if(d.type==="checkbox")return n.jsxs("div",{className:"checkbox-field",children:[n.jsxs("label",{title:T,children:[n.jsx("input",{type:"checkbox",checked:!!j,onChange:y=>a(v,d,y.target.checked)}),d.label]}),b&&n.jsx("div",{className:"field-description",children:b})]},N);if(d.type==="select"){const y=d.label==="Theme"&&v.join(".")==="WebUI.Theme";let P=j;if(y&&typeof j=="string"){const F=j.toLowerCase();F==="light"?P="Light":P="Dark"}return n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx(Me,{options:(d.options??[]).map(F=>({value:F,label:F})),value:P?{value:P,label:P}:null,onChange:F=>{const U=F?.value||"";if(a(v,d,U),y&&typeof U=="string"&&U){const fe=U.toLowerCase();document.documentElement.setAttribute("data-theme",fe),localStorage.setItem("theme",fe)}},styles:Be()}),b&&n.jsx("div",{className:"field-description",children:b}),y&&n.jsx("div",{className:"field-hint",children:"Theme changes apply immediately"})]},N)}return d.type==="number"?n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"number",value:Number(j)||0,onChange:y=>a(v,d,String(y.target.value)),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},N):d.type==="password"?n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"password",value:String(j),onChange:y=>a(v,d,y.target.value),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},N):n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"text",value:String(j),onChange:y=>a(v,d,y.target.value),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},N)});return e?n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsx("div",{className:"config-section__body field-grid",children:p})]}):n.jsx("div",{className:"field-grid",children:p})}function ls({fields:e,state:t,basePath:r,onChange:s,onDelete:a}){const i=M(t,["Name"])||"New Tracker";return n.jsxs("details",{className:"card tracker-card",open:!0,children:[n.jsxs("summary",{className:"card-header",children:[n.jsx("span",{children:i}),n.jsx("button",{className:"btn danger ghost",type:"button",onClick:a,children:n.jsx(I,{src:Te})})]}),n.jsx("div",{className:"card-body",children:n.jsx(B,{title:null,fields:e,state:t,basePath:r,onChange:s})})]})}function cs({label:e,currentName:t,placeholder:r,tooltip:s,expectedPrefix:a,onRename:i}){const[o,c]=_.useState(t),h=Gt(s)??`Rename the ${t} instance.`;_.useEffect(()=>{c(t)},[t]);const x=()=>{const p=o.trim();if(!p){c(t);return}let d=p;if(ot.test(t)){if(p==="qBit"?d="qBit":p.startsWith("qBit-")||(d=`qBit-${p}`),d!=="qBit"&&!d.match(/^qBit-.+$/)){alert(`qBit instance name must match format: qBit-NAME
|
|
1
|
+
import{u as It,f as sr,p as ir,j as n,I,q as We,t as ar,C as Je,R as Ct,i as or}from"./app.js";import{r as _}from"./table.js";import{g as lr}from"./vendor.js";import{S as ke}from"./react-select.esm.js";var Pt=Symbol.for("immer-nothing"),ct=Symbol.for("immer-draftable"),D=Symbol.for("immer-state");function $(e,...t){throw new Error(`[Immer] minified error nr: ${e}. Full error at: https://bit.ly/3cXEKWf`)}var q=Object,re=q.getPrototypeOf,ye="constructor",Ne="prototype",Ke="configurable",ge="enumerable",me="writable",oe="value",H=e=>!!e&&!!e[D];function G(e){return e?At(e)||we(e)||!!e[ct]||!!e[ye]?.[ct]||Ie(e)||Ce(e):!1}var cr=q[Ne][ye].toString(),dt=new WeakMap;function At(e){if(!e||!Ze(e))return!1;const t=re(e);if(t===null||t===q[Ne])return!0;const r=q.hasOwnProperty.call(t,ye)&&t[ye];if(r===Object)return!0;if(!te(r))return!1;let s=dt.get(r);return s===void 0&&(s=Function.toString.call(r),dt.set(r,s)),s===cr}function Ee(e,t,r=!0){ue(e)===0?(r?Reflect.ownKeys(e):q.keys(e)).forEach(a=>{t(a,e[a],e)}):e.forEach((s,a)=>t(a,s,e))}function ue(e){const t=e[D];return t?t.type_:we(e)?1:Ie(e)?2:Ce(e)?3:0}var ut=(e,t,r=ue(e))=>r===2?e.has(t):q[Ne].hasOwnProperty.call(e,t),ze=(e,t,r=ue(e))=>r===2?e.get(t):e[t],Se=(e,t,r,s=ue(e))=>{s===2?e.set(t,r):s===3?e.add(r):e[t]=r};function dr(e,t){return e===t?e!==0||1/e===1/t:e!==e&&t!==t}var we=Array.isArray,Ie=e=>e instanceof Map,Ce=e=>e instanceof Set,Ze=e=>typeof e=="object",te=e=>typeof e=="function",De=e=>typeof e=="boolean";function ur(e){const t=+e;return Number.isInteger(t)&&String(t)===e}var z=e=>e.copy_||e.base_,et=e=>e.modified_?e.copy_:e.base_;function Ge(e,t){if(Ie(e))return new Map(e);if(Ce(e))return new Set(e);if(we(e))return Array[Ne].slice.call(e);const r=At(e);if(t===!0||t==="class_only"&&!r){const s=q.getOwnPropertyDescriptors(e);delete s[D];let a=Reflect.ownKeys(s);for(let i=0;i<a.length;i++){const o=a[i],c=s[o];c[me]===!1&&(c[me]=!0,c[Ke]=!0),(c.get||c.set)&&(s[o]={[Ke]:!0,[me]:!0,[ge]:c[ge],[oe]:e[o]})}return q.create(re(e),s)}else{const s=re(e);if(s!==null&&r)return{...e};const a=q.create(s);return q.assign(a,e)}}function tt(e,t=!1){return Pe(e)||H(e)||!G(e)||(ue(e)>1&&q.defineProperties(e,{set:pe,add:pe,clear:pe,delete:pe}),q.freeze(e),t&&Ee(e,(r,s)=>{tt(s,!0)},!1)),e}function fr(){$(2)}var pe={[oe]:fr};function Pe(e){return e===null||!Ze(e)?!0:q.isFrozen(e)}var xe="MapSet",He="Patches",ft="ArrayMethods",Ot={};function X(e){const t=Ot[e];return t||$(0,e),t}var ht=e=>!!Ot[e],le,Ft=()=>le,hr=(e,t)=>({drafts_:[],parent_:e,immer_:t,canAutoFreeze_:!0,unfinalizedDrafts_:0,handledSet_:new Set,processedForPatches_:new Set,mapSetPlugin_:ht(xe)?X(xe):void 0,arrayMethodsPlugin_:ht(ft)?X(ft):void 0});function pt(e,t){t&&(e.patchPlugin_=X(He),e.patches_=[],e.inversePatches_=[],e.patchListener_=t)}function Ve(e){Qe(e),e.drafts_.forEach(pr),e.drafts_=null}function Qe(e){e===le&&(le=e.parent_)}var mt=e=>le=hr(le,e);function pr(e){const t=e[D];t.type_===0||t.type_===1?t.revoke_():t.revoked_=!0}function bt(e,t){t.unfinalizedDrafts_=t.drafts_.length;const r=t.drafts_[0];if(e!==void 0&&e!==r){r[D].modified_&&(Ve(t),$(4)),G(e)&&(e=yt(t,e));const{patchPlugin_:a}=t;a&&a.generateReplacementPatches_(r[D].base_,e,t)}else e=yt(t,r);return mr(t,e,!0),Ve(t),t.patches_&&t.patchListener_(t.patches_,t.inversePatches_),e!==Pt?e:void 0}function yt(e,t){if(Pe(t))return t;const r=t[D];if(!r)return ve(t,e.handledSet_,e);if(!Ae(r,e))return t;if(!r.modified_)return r.base_;if(!r.finalized_){const{callbacks_:s}=r;if(s)for(;s.length>0;)s.pop()(e);Dt(r,e)}return r.copy_}function mr(e,t,r=!1){!e.parent_&&e.immer_.autoFreeze_&&e.canAutoFreeze_&&tt(t,r)}function Mt(e){e.finalized_=!0,e.scope_.unfinalizedDrafts_--}var Ae=(e,t)=>e.scope_===t,br=[];function kt(e,t,r,s){const a=z(e),i=e.type_;if(s!==void 0&&ze(a,s,i)===t){Se(a,s,r,i);return}if(!e.draftLocations_){const c=e.draftLocations_=new Map;Ee(a,(h,x)=>{if(H(x)){const p=c.get(x)||[];p.push(h),c.set(x,p)}})}const o=e.draftLocations_.get(t)??br;for(const c of o)Se(a,c,r,i)}function yr(e,t,r){e.callbacks_.push(function(a){const i=t;if(!i||!Ae(i,a))return;a.mapSetPlugin_?.fixSetContents(i);const o=et(i);kt(e,i.draft_??i,o,r),Dt(i,a)})}function Dt(e,t){if(e.modified_&&!e.finalized_&&(e.type_===3||e.type_===1&&e.allIndicesReassigned_||(e.assigned_?.size??0)>0)){const{patchPlugin_:s}=t;if(s){const a=s.getPath(e);a&&s.generatePatches_(e,a,t)}Mt(e)}}function gr(e,t,r){const{scope_:s}=e;if(H(r)){const a=r[D];Ae(a,s)&&a.callbacks_.push(function(){be(e);const o=et(a);kt(e,r,o,t)})}else G(r)&&e.callbacks_.push(function(){const i=z(e);e.type_===3?i.has(r)&&ve(r,s.handledSet_,s):ze(i,t,e.type_)===r&&s.drafts_.length>1&&(e.assigned_.get(t)??!1)===!0&&e.copy_&&ve(ze(e.copy_,t,e.type_),s.handledSet_,s)})}function ve(e,t,r){return!r.immer_.autoFreeze_&&r.unfinalizedDrafts_<1||H(e)||t.has(e)||!G(e)||Pe(e)||(t.add(e),Ee(e,(s,a)=>{if(H(a)){const i=a[D];if(Ae(i,r)){const o=et(i);Se(e,s,o,e.type_),Mt(i)}}else G(a)&&ve(a,t,r)})),e}function Sr(e,t){const r=we(e),s={type_:r?1:0,scope_:t?t.scope_:Ft(),modified_:!1,finalized_:!1,assigned_:void 0,parent_:t,base_:e,draft_:null,copy_:null,revoke_:null,isManual_:!1,callbacks_:void 0};let a=s,i=_e;r&&(a=[s],i=ce);const{revoke:o,proxy:c}=Proxy.revocable(a,i);return s.draft_=c,s.revoke_=o,[c,s]}var _e={get(e,t){if(t===D)return e;let r=e.scope_.arrayMethodsPlugin_;const s=e.type_===1&&typeof t=="string";if(s&&r?.isArrayOperationMethod(t))return r.createMethodInterceptor(e,t);const a=z(e);if(!ut(a,t,e.type_))return xr(e,a,t);const i=a[t];if(e.finalized_||!G(i)||s&&e.operationMethod&&r?.isMutatingArrayMethod(e.operationMethod)&&ur(t))return i;if(i===Ue(e.base_,t)){be(e);const o=e.type_===1?+t:t,c=Xe(e.scope_,i,e,o);return e.copy_[o]=c}return i},has(e,t){return t in z(e)},ownKeys(e){return Reflect.ownKeys(z(e))},set(e,t,r){const s=Ut(z(e),t);if(s?.set)return s.set.call(e.draft_,r),!0;if(!e.modified_){const a=Ue(z(e),t),i=a?.[D];if(i&&i.base_===r)return e.copy_[t]=r,e.assigned_.set(t,!1),!0;if(dr(r,a)&&(r!==void 0||ut(e.base_,t,e.type_)))return!0;be(e),Ye(e)}return e.copy_[t]===r&&(r!==void 0||t in e.copy_)||Number.isNaN(r)&&Number.isNaN(e.copy_[t])||(e.copy_[t]=r,e.assigned_.set(t,!0),gr(e,t,r)),!0},deleteProperty(e,t){return be(e),Ue(e.base_,t)!==void 0||t in e.base_?(e.assigned_.set(t,!1),Ye(e)):e.assigned_.delete(t),e.copy_&&delete e.copy_[t],!0},getOwnPropertyDescriptor(e,t){const r=z(e),s=Reflect.getOwnPropertyDescriptor(r,t);return s&&{[me]:!0,[Ke]:e.type_!==1||t!=="length",[ge]:s[ge],[oe]:r[t]}},defineProperty(){$(11)},getPrototypeOf(e){return re(e.base_)},setPrototypeOf(){$(12)}},ce={};for(let e in _e){let t=_e[e];ce[e]=function(){const r=arguments;return r[0]=r[0][0],t.apply(this,r)}}ce.deleteProperty=function(e,t){return ce.set.call(this,e,t,void 0)};ce.set=function(e,t,r){return _e.set.call(this,e[0],t,r,e[0])};function Ue(e,t){const r=e[D];return(r?z(r):e)[t]}function xr(e,t,r){const s=Ut(t,r);return s?oe in s?s[oe]:s.get?.call(e.draft_):void 0}function Ut(e,t){if(!(t in e))return;let r=re(e);for(;r;){const s=Object.getOwnPropertyDescriptor(r,t);if(s)return s;r=re(r)}}function Ye(e){e.modified_||(e.modified_=!0,e.parent_&&Ye(e.parent_))}function be(e){e.copy_||(e.assigned_=new Map,e.copy_=Ge(e.base_,e.scope_.immer_.useStrictShallowCopy_))}var vr=class{constructor(e){this.autoFreeze_=!0,this.useStrictShallowCopy_=!1,this.useStrictIteration_=!1,this.produce=(t,r,s)=>{if(te(t)&&!te(r)){const i=r;r=t;const o=this;return function(h=i,...x){return o.produce(h,p=>r.call(this,p,...x))}}te(r)||$(6),s!==void 0&&!te(s)&&$(7);let a;if(G(t)){const i=mt(this),o=Xe(i,t,void 0);let c=!0;try{a=r(o),c=!1}finally{c?Ve(i):Qe(i)}return pt(i,s),bt(a,i)}else if(!t||!Ze(t)){if(a=r(t),a===void 0&&(a=t),a===Pt&&(a=void 0),this.autoFreeze_&&tt(a,!0),s){const i=[],o=[];X(He).generateReplacementPatches_(t,a,{patches_:i,inversePatches_:o}),s(i,o)}return a}else $(1,t)},this.produceWithPatches=(t,r)=>{if(te(t))return(o,...c)=>this.produceWithPatches(o,h=>t(h,...c));let s,a;return[this.produce(t,r,(o,c)=>{s=o,a=c}),s,a]},De(e?.autoFreeze)&&this.setAutoFreeze(e.autoFreeze),De(e?.useStrictShallowCopy)&&this.setUseStrictShallowCopy(e.useStrictShallowCopy),De(e?.useStrictIteration)&&this.setUseStrictIteration(e.useStrictIteration)}createDraft(e){G(e)||$(8),H(e)&&(e=_r(e));const t=mt(this),r=Xe(t,e,void 0);return r[D].isManual_=!0,Qe(t),r}finishDraft(e,t){const r=e&&e[D];(!r||!r.isManual_)&&$(9);const{scope_:s}=r;return pt(s,t),bt(void 0,s)}setAutoFreeze(e){this.autoFreeze_=e}setUseStrictShallowCopy(e){this.useStrictShallowCopy_=e}setUseStrictIteration(e){this.useStrictIteration_=e}shouldUseStrictIteration(){return this.useStrictIteration_}applyPatches(e,t){let r;for(r=t.length-1;r>=0;r--){const a=t[r];if(a.path.length===0&&a.op==="replace"){e=a.value;break}}r>-1&&(t=t.slice(r+1));const s=X(He).applyPatches_;return H(e)?s(e,t):this.produce(e,a=>s(a,t))}};function Xe(e,t,r,s){const[a,i]=Ie(t)?X(xe).proxyMap_(t,r):Ce(t)?X(xe).proxySet_(t,r):Sr(t,r);return(r?.scope_??Ft()).drafts_.push(a),i.callbacks_=r?.callbacks_??[],i.key_=s,r&&s!==void 0?yr(r,i,s):i.callbacks_.push(function(h){h.mapSetPlugin_?.fixSetContents(i);const{patchPlugin_:x}=h;i.modified_&&x&&x.generatePatches_(i,[],h)}),a}function _r(e){return H(e)||$(10,e),qt(e)}function qt(e){if(!G(e)||Pe(e))return e;const t=e[D];let r,s=!0;if(t){if(!t.modified_)return t.base_;t.finalized_=!0,r=Ge(e,t.scope_.immer_.useStrictShallowCopy_),s=t.scope_.immer_.shouldUseStrictIteration()}else r=Ge(e,!0);return Ee(r,(a,i)=>{Se(r,a,qt(i))},s),t&&(t.finalized_=!1),r}var Rr=new vr,V=Rr.produce,qe,gt;function jr(){return gt||(gt=1,qe=function e(t,r){if(t===r)return!0;if(t&&r&&typeof t=="object"&&typeof r=="object"){if(t.constructor!==r.constructor)return!1;var s,a,i;if(Array.isArray(t)){if(s=t.length,s!=r.length)return!1;for(a=s;a--!==0;)if(!e(t[a],r[a]))return!1;return!0}if(t.constructor===RegExp)return t.source===r.source&&t.flags===r.flags;if(t.valueOf!==Object.prototype.valueOf)return t.valueOf()===r.valueOf();if(t.toString!==Object.prototype.toString)return t.toString()===r.toString();if(i=Object.keys(t),s=i.length,s!==Object.keys(r).length)return!1;for(a=s;a--!==0;)if(!Object.prototype.hasOwnProperty.call(r,i[a]))return!1;for(a=s;a--!==0;){var o=i[a];if(!e(t[o],r[o]))return!1}return!0}return t!==t&&r!==r}),qe}var Tr=jr();const St=lr(Tr);var Nr=typeof global=="object"&&global&&global.Object===Object&&global,Er=typeof self=="object"&&self&&self.Object===Object&&self,rt=Nr||Er||Function("return this")(),ne=rt.Symbol,Lt=Object.prototype,wr=Lt.hasOwnProperty,Ir=Lt.toString,ie=ne?ne.toStringTag:void 0;function Cr(e){var t=wr.call(e,ie),r=e[ie];try{e[ie]=void 0;var s=!0}catch{}var a=Ir.call(e);return s&&(t?e[ie]=r:delete e[ie]),a}var Pr=Object.prototype,Ar=Pr.toString;function Or(e){return Ar.call(e)}var Fr="[object Null]",Mr="[object Undefined]",xt=ne?ne.toStringTag:void 0;function Bt(e){return e==null?e===void 0?Mr:Fr:xt&&xt in Object(e)?Cr(e):Or(e)}function kr(e){return e!=null&&typeof e=="object"}var Dr="[object Symbol]";function nt(e){return typeof e=="symbol"||kr(e)&&Bt(e)==Dr}function Ur(e,t){for(var r=-1,s=e==null?0:e.length,a=Array(s);++r<s;)a[r]=t(e[r],r,e);return a}var st=Array.isArray,vt=ne?ne.prototype:void 0,_t=vt?vt.toString:void 0;function $t(e){if(typeof e=="string")return e;if(st(e))return Ur(e,$t)+"";if(nt(e))return _t?_t.call(e):"";var t=e+"";return t=="0"&&1/e==-1/0?"-0":t}function Re(e){var t=typeof e;return e!=null&&(t=="object"||t=="function")}var qr="[object AsyncFunction]",Lr="[object Function]",Br="[object GeneratorFunction]",$r="[object Proxy]";function Wr(e){if(!Re(e))return!1;var t=Bt(e);return t==Lr||t==Br||t==qr||t==$r}var Le=rt["__core-js_shared__"],Rt=(function(){var e=/[^.]+$/.exec(Le&&Le.keys&&Le.keys.IE_PROTO||"");return e?"Symbol(src)_1."+e:""})();function Kr(e){return!!Rt&&Rt in e}var zr=Function.prototype,Gr=zr.toString;function Hr(e){if(e!=null){try{return Gr.call(e)}catch{}try{return e+""}catch{}}return""}var Vr=/[\\^$.*+?()[\]{}|]/g,Qr=/^\[object .+?Constructor\]$/,Yr=Function.prototype,Xr=Object.prototype,Jr=Yr.toString,Zr=Xr.hasOwnProperty,en=RegExp("^"+Jr.call(Zr).replace(Vr,"\\$&").replace(/hasOwnProperty|(function).*?(?=\\\()| for .+?(?=\\\])/g,"$1.*?")+"$");function tn(e){if(!Re(e)||Kr(e))return!1;var t=Wr(e)?en:Qr;return t.test(Hr(e))}function rn(e,t){return e?.[t]}function it(e,t){var r=rn(e,t);return tn(r)?r:void 0}var jt=(function(){try{var e=it(Object,"defineProperty");return e({},"",{}),e}catch{}})(),nn=9007199254740991,sn=/^(?:0|[1-9]\d*)$/;function an(e,t){var r=typeof e;return t=t??nn,!!t&&(r=="number"||r!="symbol"&&sn.test(e))&&e>-1&&e%1==0&&e<t}function on(e,t,r){t=="__proto__"&&jt?jt(e,t,{configurable:!0,enumerable:!0,value:r,writable:!0}):e[t]=r}function Wt(e,t){return e===t||e!==e&&t!==t}var ln=Object.prototype,cn=ln.hasOwnProperty;function dn(e,t,r){var s=e[t];(!(cn.call(e,t)&&Wt(s,r))||r===void 0&&!(t in e))&&on(e,t,r)}var un=/\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,fn=/^\w*$/;function hn(e,t){if(st(e))return!1;var r=typeof e;return r=="number"||r=="symbol"||r=="boolean"||e==null||nt(e)?!0:fn.test(e)||!un.test(e)||t!=null&&e in Object(t)}var de=it(Object,"create");function pn(){this.__data__=de?de(null):{},this.size=0}function mn(e){var t=this.has(e)&&delete this.__data__[e];return this.size-=t?1:0,t}var bn="__lodash_hash_undefined__",yn=Object.prototype,gn=yn.hasOwnProperty;function Sn(e){var t=this.__data__;if(de){var r=t[e];return r===bn?void 0:r}return gn.call(t,e)?t[e]:void 0}var xn=Object.prototype,vn=xn.hasOwnProperty;function _n(e){var t=this.__data__;return de?t[e]!==void 0:vn.call(t,e)}var Rn="__lodash_hash_undefined__";function jn(e,t){var r=this.__data__;return this.size+=this.has(e)?0:1,r[e]=de&&t===void 0?Rn:t,this}function J(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}J.prototype.clear=pn;J.prototype.delete=mn;J.prototype.get=Sn;J.prototype.has=_n;J.prototype.set=jn;function Tn(){this.__data__=[],this.size=0}function Oe(e,t){for(var r=e.length;r--;)if(Wt(e[r][0],t))return r;return-1}var Nn=Array.prototype,En=Nn.splice;function wn(e){var t=this.__data__,r=Oe(t,e);if(r<0)return!1;var s=t.length-1;return r==s?t.pop():En.call(t,r,1),--this.size,!0}function In(e){var t=this.__data__,r=Oe(t,e);return r<0?void 0:t[r][1]}function Cn(e){return Oe(this.__data__,e)>-1}function Pn(e,t){var r=this.__data__,s=Oe(r,e);return s<0?(++this.size,r.push([e,t])):r[s][1]=t,this}function se(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}se.prototype.clear=Tn;se.prototype.delete=wn;se.prototype.get=In;se.prototype.has=Cn;se.prototype.set=Pn;var An=it(rt,"Map");function On(){this.size=0,this.__data__={hash:new J,map:new(An||se),string:new J}}function Fn(e){var t=typeof e;return t=="string"||t=="number"||t=="symbol"||t=="boolean"?e!=="__proto__":e===null}function Fe(e,t){var r=e.__data__;return Fn(t)?r[typeof t=="string"?"string":"hash"]:r.map}function Mn(e){var t=Fe(this,e).delete(e);return this.size-=t?1:0,t}function kn(e){return Fe(this,e).get(e)}function Dn(e){return Fe(this,e).has(e)}function Un(e,t){var r=Fe(this,e),s=r.size;return r.set(e,t),this.size+=r.size==s?0:1,this}function Z(e){var t=-1,r=e==null?0:e.length;for(this.clear();++t<r;){var s=e[t];this.set(s[0],s[1])}}Z.prototype.clear=On;Z.prototype.delete=Mn;Z.prototype.get=kn;Z.prototype.has=Dn;Z.prototype.set=Un;var qn="Expected a function";function at(e,t){if(typeof e!="function"||t!=null&&typeof t!="function")throw new TypeError(qn);var r=function(){var s=arguments,a=t?t.apply(this,s):s[0],i=r.cache;if(i.has(a))return i.get(a);var o=e.apply(this,s);return r.cache=i.set(a,o)||i,o};return r.cache=new(at.Cache||Z),r}at.Cache=Z;var Ln=500;function Bn(e){var t=at(e,function(s){return r.size===Ln&&r.clear(),s}),r=t.cache;return t}var $n=/[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g,Wn=/\\(\\)?/g,Kn=Bn(function(e){var t=[];return e.charCodeAt(0)===46&&t.push(""),e.replace($n,function(r,s,a,i){t.push(a?i.replace(Wn,"$1"):s||r)}),t});function zn(e){return e==null?"":$t(e)}function Kt(e,t){return st(e)?e:hn(e,t)?[e]:Kn(zn(e))}function zt(e){if(typeof e=="string"||nt(e))return e;var t=e+"";return t=="0"&&1/e==-1/0?"-0":t}function Gn(e,t){t=Kt(t,e);for(var r=0,s=t.length;e!=null&&r<s;)e=e[zt(t[r++])];return r&&r==s?e:void 0}function Gt(e,t,r){var s=e==null?void 0:Gn(e,t);return s===void 0?r:s}function Hn(e,t,r,s){if(!Re(e))return e;t=Kt(t,e);for(var a=-1,i=t.length,o=i-1,c=e;c!=null&&++a<i;){var h=zt(t[a]),x=r;if(h==="__proto__"||h==="constructor"||h==="prototype")return e;if(a!=o){var p=c[h];x=void 0,x===void 0&&(x=Re(p)?p:an(t[a+1])?[]:{})}dn(c,h,x),c=c[h]}return e}function Vn(e,t,r){return e==null?e:Hn(e,t,r)}const L={"Settings.ConfigVersion":"Internal schema version managed automatically by qBitrr for config migrations. DO NOT manually modify this value.","Settings.ConsoleLevel":"Level of logging; choose between CRITICAL, ERROR, WARNING, NOTICE, INFO, DEBUG, TRACE.","Settings.Logging":"Enable writing log output to files.","Settings.CompletedDownloadFolder":"Folder where completed downloads are stored. Replace backslashes with forward slashes.","Settings.FreeSpace":"Desired free space threshold (use K, M, G, T suffix). Set to -1 to disable the free space guard.","Settings.FreeSpaceFolder":"Path used when checking free space. Replace backslashes with forward slashes.","Settings.AutoPauseResume":"Automatically pause and resume torrents in response to the free space guard.","Settings.NoInternetSleepTimer":"Delay, in seconds, before retrying when no internet connectivity is detected.","Settings.LoopSleepTimer":"Delay, in seconds, between processing passes when monitoring torrents.","Settings.SearchLoopDelay":"Delay, in seconds, between media search requests.","Settings.FailedCategory":"Category that marks torrents as failed.","Settings.RecheckCategory":"Category that triggers recheck handling.","Settings.Tagless":"Enable tagless operation when categories are not used.","Settings.IgnoreTorrentsYoungerThan":"Ignore torrents younger than this many seconds when evaluating failures.","Settings.PingURLS":"Hostnames used to test for internet connectivity. They are pinged frequently.","Settings.FFprobeAutoUpdate":"Download and update the bundled ffprobe binary automatically.","Settings.AutoUpdateEnabled":"Enable the background worker that periodically checks for qBitrr updates.","Settings.AutoUpdateCron":"Cron expression describing when to check for updates (default weekly Sunday at 03:00).","Settings.AutoRestartProcesses":"Automatically restart worker processes that crash unexpectedly. Recommended to keep enabled for reliability.","Settings.MaxProcessRestarts":"Maximum number of times a worker process can be restarted within the restart window before auto-restart is disabled. Prevents infinite crash loops.","Settings.ProcessRestartWindow":"Time window in seconds for tracking restart attempts. If MaxProcessRestarts is exceeded within this window, auto-restart is disabled for that process.","Settings.ProcessRestartDelay":"Delay in seconds before restarting a crashed worker process. Gives time for transient issues to resolve.","WebUI.Host":"Interface address for the built-in WebUI. 0.0.0.0 binds on all interfaces.","WebUI.Port":"Port number for the built-in WebUI.","WebUI.Token":"Optional bearer token required by the WebUI/API. Leave empty to disable authentication.","WebUI.LiveArr":"Enable live updates for Arr views.","WebUI.GroupSonarr":"Group Sonarr views by series and seasons in collapsible sections.","WebUI.GroupLidarr":"Group Lidarr views by artist and albums in collapsible sections.","WebUI.Theme":"Choose the visual theme for the WebUI (light or dark).","qBit.Disabled":"Disable qBitrr's direct qBittorrent integration (headless mode for search-only setups).","qBit.Host":"qBittorrent WebUI host or IP address.","qBit.Port":"qBittorrent WebUI port.","qBit.UserName":"qBittorrent WebUI username.","qBit.Password":"qBittorrent WebUI password. Remove this if authentication is bypassed for the host.",Disabled:"Disable this qBittorrent instance (headless mode for search-only setups).",Host:"qBittorrent WebUI host or IP address.",Port:"qBittorrent WebUI port.",UserName:"qBittorrent WebUI username.",Password:"qBittorrent WebUI password. Remove this if authentication is bypassed for the host.","ARR.Managed":"Toggle whether this Servarr instance is actively managed by qBitrr.","ARR.URI":"Servarr URL, including protocol and port if needed (for example http://localhost:8989).","ARR.APIKey":"Servarr API key from Settings > General > Security.","ARR.Category":"qBittorrent category applied by the Servarr instance to its downloads.","ARR.ReSearch":"Re-run searches for failed torrents that qBitrr removes.","ARR.importMode":"Preferred import mode (Move, Copy, or Auto) when Servarr grabs completed files.","ARR.RssSyncTimer":"Interval, in minutes, between RSS sync requests (0 disables the task).","ARR.RefreshDownloadsTimer":"Interval, in minutes, between queue refresh requests (0 disables the task).","ARR.ArrErrorCodesToBlocklist":"List of Servarr error messages that should trigger blocklisting and cleanup.","EntrySearch.SearchMissing":"Search for missing media items.","EntrySearch.AlsoSearchSpecials":"Include season 0 specials in missing searches.","EntrySearch.Unmonitored":"Include unmonitored series or episodes in searches.","EntrySearch.SearchLimit":"Maximum number of concurrent search tasks (Servarr enforces its own limits).","EntrySearch.SearchByYear":"Order searches by the year the episode or movie first aired.","EntrySearch.SearchInReverse":"Reverse search order (search oldest to newest instead of newest to oldest).","EntrySearch.SearchRequestsEvery":"Delay, in seconds, between checking for new Overseerr/Ombi requests. After processing all pending requests, qBitrr waits this long before checking again. Default: 300 seconds (5 minutes).","EntrySearch.DoUpgradeSearch":"Search for improved releases even if a file already exists.","EntrySearch.QualityUnmetSearch":"Search again when the quality requirements were not met.","EntrySearch.CustomFormatUnmetSearch":"Search again when the minimum custom format score was not met.","EntrySearch.ForceMinimumCustomFormat":"Automatically remove torrents that do not meet the minimum custom format score.","EntrySearch.SearchAgainOnSearchCompletion":"Restart the search loop when the configured year range is exhausted.","EntrySearch.UseTempForMissing":"Switch to temporary profiles when searching for missing media.","EntrySearch.KeepTempProfile":"Do not revert to the main profile after using the temp profile.","EntrySearch.MainQualityProfile":"[DEPRECATED - Use QualityProfileMappings instead] Primary quality profile names, in the same order as the temporary profiles.","EntrySearch.TempQualityProfile":"[DEPRECATED - Use QualityProfileMappings instead] Temporary quality profile names, paired with the primary profiles.","EntrySearch.SearchBySeries":"Search by entire series instead of individual episodes when applicable.","EntrySearch.PrioritizeTodaysReleases":"Prioritise items released today (similar to RSS prioritisation).","EntrySearch.Ombi.SearchOmbiRequests":"Pull pending Ombi requests when SearchMissing is enabled.","EntrySearch.Ombi.OmbiURI":"Ombi server URL.","EntrySearch.Ombi.OmbiAPIKey":"Ombi API key.","EntrySearch.Ombi.ApprovedOnly":"Only process Ombi requests that are approved.","EntrySearch.Overseerr.SearchOverseerrRequests":"Pull Overseerr requests when SearchMissing is enabled.","EntrySearch.Overseerr.OverseerrURI":"Overseerr server URL.","EntrySearch.Overseerr.OverseerrAPIKey":"Overseerr API key.","EntrySearch.Overseerr.ApprovedOnly":"Only process Overseerr requests that are approved.","EntrySearch.Overseerr.Is4K":"Treat this Overseerr configuration as 4K specific.","Torrent.CaseSensitiveMatches":"When enabled, regex matches will respect case; otherwise they are case-insensitive.","Torrent.FolderExclusionRegex":"Regex patterns that exclude folders outright (full-name match).","Torrent.FileNameExclusionRegex":"Regex patterns that exclude individual files based on the file name.","Torrent.FileExtensionAllowlist":"Allowed file extensions (or regex) for downloads; leave empty to allow all.","Torrent.AutoDelete":"Automatically delete files that are not recognised as media.","Torrent.IgnoreTorrentsYoungerThan":"Ignore torrents younger than this many seconds for failure handling.","Torrent.MaximumETA":"Maximum allowed remaining ETA in seconds; values above this are considered stalled.","Torrent.MaximumDeletablePercentage":"Upper bound for completion percentage when deciding to delete a torrent.","Torrent.DoNotRemoveSlow":"Ignore slow torrents when pruning.","Torrent.StalledDelay":"Minutes to allow stalled torrents before taking action (-1 disables, 0 is infinite).","Torrent.ReSearchStalled":"Re-run searches for stalled torrents before or after removal depending on configuration.","Torrent.RemoveDeadTrackers":"Remove trackers flagged as dead.","Torrent.RemoveTrackerWithMessage":"Tracker status messages that should trigger tracker removal when RemoveDeadTrackers is enabled.","Torrent.SeedingMode.DownloadRateLimitPerTorrent":"Per-torrent download rate limit in bytes per second (-1 disables the limit).","Torrent.SeedingMode.UploadRateLimitPerTorrent":"Per-torrent upload rate limit in bytes per second (-1 disables the limit).","Torrent.SeedingMode.MaxUploadRatio":"Maximum allowed upload ratio (-1 disables the limit).","Torrent.SeedingMode.MaxSeedingTime":"Maximum seeding duration in seconds (-1 disables the limit).","Torrent.SeedingMode.RemoveTorrent":"Removal policy: -1 do not remove, 1 remove on ratio, 2 remove on time, 3 remove on ratio or time, 4 remove on ratio and time."};function Tt(e){const t=e.join(".");if(L[t])return L[t];if(e.length>1){if(e[0]&&/^qBit(-.*)?$/i.test(e[0])){const c=["qBit",...e.slice(1)].join(".");if(L[c])return L[c]}const a=["ARR",...e.slice(1)].join(".");if(L[a])return L[a];const i=["EntrySearch",...e.slice(2)].join(".");if(e[1]==="EntrySearch"&&L[i])return L[i];const o=["Torrent",...e.slice(2)].join(".");if(e[1]==="Torrent"&&L[o])return L[o]}const r=e[e.length-1];return L[r]}const Qn="/static/assets/visibility.svg",je="/static/assets/plus.svg",Me="/static/assets/check-mark.svg",Te="/static/assets/trash.svg",ot=/(rad|son|lid)arr/i,lt=/^qBit(-.*)?$/i,Be=()=>{const e=document.documentElement.getAttribute("data-theme")==="dark";return{control:t=>({...t,background:e?"#0f131a":"#ffffff",color:e?"#eaeef2":"#1d1d1f",borderColor:e?"#2a2f36":"#d2d2d7",minHeight:"38px",boxShadow:"none","&:hover":{borderColor:e?"#3a4149":"#b8b8bd"}}),menu:t=>({...t,background:e?"#0f131a":"#ffffff",borderColor:e?"#2a2f36":"#d2d2d7",border:`1px solid ${e?"#2a2f36":"#d2d2d7"}`}),option:(t,r)=>({...t,background:r.isFocused?e?"rgba(122, 162, 247, 0.15)":"rgba(0, 113, 227, 0.1)":e?"#0f131a":"#ffffff",color:e?"#eaeef2":"#1d1d1f","&:active":{background:e?"rgba(122, 162, 247, 0.25)":"rgba(0, 113, 227, 0.2)"}}),singleValue:t=>({...t,color:e?"#eaeef2":"#1d1d1f"}),input:t=>({...t,color:e?"#eaeef2":"#1d1d1f"}),placeholder:t=>({...t,color:e?"#9aa3ac":"#6e6e73"}),menuList:t=>({...t,padding:"4px"})}},Q=e=>String(e).split(",").map(t=>t.trim()).filter(Boolean),Y=e=>Array.isArray(e)?e.join(", "):String(e??""),Yn=["Move","Copy","Auto"],$e=["Do not remove (-1)","On max upload ratio (1)","On max seeding time (2)","On ratio OR time (3)","On ratio AND time (4)"],Xn=/(.+?[.!?])(\s|$)/;function Ht(e){if(!e)return;const t=e.trim();if(!t)return;const r=t.match(Xn),s=r?r[1]:t;return s.length>160?`${s.slice(0,157)}…`:s}const Vt=[{label:"Console Level",path:["Settings","ConsoleLevel"],type:"select",options:["CRITICAL","ERROR","WARNING","NOTICE","INFO","DEBUG","TRACE"],required:!0},{label:"Logging",path:["Settings","Logging"],type:"checkbox"},{label:"Completed Download Folder",path:["Settings","CompletedDownloadFolder"],type:"text",required:!0,validate:e=>{const t=String(e??"").trim();if(!t||t.toUpperCase()==="CHANGE_ME")return"Completed Download Folder must be set to a valid path."}},{label:"Free Space",path:["Settings","FreeSpace"],type:"text",required:!0,validate:e=>{const t=String(e??"").trim();if(!t)return"Free Space must be provided.";if(t!=="-1"&&!/^-?\d+(\.\d+)?[KMGTP]?$/i.test(t))return"Free Space must be -1 or a number optionally suffixed with K, M, G, T, or P."}},{label:"Free Space Folder",path:["Settings","FreeSpaceFolder"],type:"text",validate:(e,t)=>{const r=k(t.root,["Settings","FreeSpace"]);if(!(String(r??"").trim()!=="-1"))return;const a=String(e??"").trim();if(!a||a.toUpperCase()==="CHANGE_ME")return"Free Space Folder is required when Free Space monitoring is enabled."}},{label:"Auto Pause/Resume",path:["Settings","AutoPauseResume"],type:"checkbox"},{label:"No Internet Sleep (s)",path:["Settings","NoInternetSleepTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"No Internet Sleep must be a non-negative number."}},{label:"Loop Sleep (s)",path:["Settings","LoopSleepTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Loop Sleep must be a non-negative number."}},{label:"Search Loop Delay (s)",path:["Settings","SearchLoopDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Search Loop Delay must be a non-negative number."}},{label:"Failed Category",path:["Settings","FailedCategory"],type:"text"},{label:"Recheck Category",path:["Settings","RecheckCategory"],type:"text"},{label:"Tagless",path:["Settings","Tagless"],type:"checkbox"},{label:"Ignore Torrents Younger Than",path:["Settings","IgnoreTorrentsYoungerThan"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Ignore Torrents Younger Than must be a non-negative number."}},{label:"Ping URLs",path:["Settings","PingURLS"],type:"text",parse:Q,format:Y,placeholder:"one.one.one.one, dns.google.com"},{label:"FFprobe Auto Update",path:["Settings","FFprobeAutoUpdate"],type:"checkbox"},{label:"Auto Update Enabled",path:["Settings","AutoUpdateEnabled"],type:"checkbox"},{label:"Auto Update Cron",path:["Settings","AutoUpdateCron"],type:"text",placeholder:"0 3 * * 0",required:!0,validate:e=>{const r=String(e??"").trim().split(/\s+/).filter(Boolean);if(r.length<5||r.length>6)return"Auto Update Cron must contain 5 or 6 space-separated fields."}},{label:"Auto-Restart Processes",path:["Settings","AutoRestartProcesses"],type:"checkbox"},{label:"Max Process Restarts",path:["Settings","MaxProcessRestarts"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Max Process Restarts must be at least 1."}},{label:"Process Restart Window (s)",path:["Settings","ProcessRestartWindow"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Process Restart Window must be at least 1 second."}},{label:"Process Restart Delay (s)",path:["Settings","ProcessRestartDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Process Restart Delay must be a non-negative number."}}],Qt=[{label:"WebUI Host",path:["WebUI","Host"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"WebUI Host is required."}},{label:"WebUI Port",path:["WebUI","Port"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isInteger(t)||t<1||t>65535)return"WebUI Port must be between 1 and 65535."}},{label:"WebUI Token",path:["WebUI","Token"],type:"password",secure:!0,fullWidth:!0}],Yt=[{label:"Display Name",type:"text",placeholder:"qBit-seedbox",sectionName:!0},{label:"Disabled",path:["Disabled"],type:"checkbox"},{label:"Host",path:["Host"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"qBit Host is required."}},{label:"Port",path:["Port"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isInteger(t)||t<1||t>65535)return"qBit Port must be between 1 and 65535."}},{label:"UserName",path:["UserName"],type:"text"},{label:"Password",path:["Password"],type:"password",secure:!0}],Jn=[{label:"Display Name",type:"text",placeholder:"Sonarr-TV",sectionName:!0},{label:"Managed",path:["Managed"],type:"checkbox"},{label:"URI",path:["URI"],type:"text",placeholder:"http://host:port",required:!0,validate:(e,t)=>{const r=String(e??"").trim();if(k(t.section??{},["Managed"])&&(!r||r.toUpperCase()==="CHANGE_ME"))return"URI must be set to a valid URL when the instance is managed."}},{label:"API Key",path:["APIKey"],type:"password",secure:!0,required:!0,validate:(e,t)=>{const r=String(e??"").trim();if(k(t.section??{},["Managed"])&&(!r||r.toUpperCase()==="CHANGE_ME"))return"API Key must be provided when the instance is managed."}},{label:"Category",path:["Category"],type:"text",required:!0,validate:e=>{if(!String(e??"").trim())return"Category is required."}},{label:"Re-search",path:["ReSearch"],type:"checkbox"},{label:"Import Mode",path:["importMode"],type:"select",options:Yn,required:!0},{label:"RSS Sync Timer (min)",path:["RssSyncTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"RSS Sync Timer must be a non-negative number."}},{label:"Refresh Downloads Timer (min)",path:["RefreshDownloadsTimer"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Refresh Downloads Timer must be a non-negative number."}},{label:"Arr Error Codes To Blocklist",path:["ArrErrorCodesToBlocklist"],type:"text",parse:Q,format:Y}],Zn=[{label:"Search Missing",path:["EntrySearch","SearchMissing"],type:"checkbox"},{label:"Also Search Specials",path:["EntrySearch","AlsoSearchSpecials"],type:"checkbox"},{label:"Unmonitored",path:["EntrySearch","Unmonitored"],type:"checkbox"},{label:"Do Upgrade Search",path:["EntrySearch","DoUpgradeSearch"],type:"checkbox"},{label:"Quality Unmet Search",path:["EntrySearch","QualityUnmetSearch"],type:"checkbox"},{label:"Custom Format Unmet Search",path:["EntrySearch","CustomFormatUnmetSearch"],type:"checkbox"},{label:"Force Minimum Custom Format",path:["EntrySearch","ForceMinimumCustomFormat"],type:"checkbox"},{label:"Search Limit",path:["EntrySearch","SearchLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Search Limit must be at least 1."}},{label:"Search By Year",path:["EntrySearch","SearchByYear"],type:"checkbox"},{label:"Search In Reverse",path:["EntrySearch","SearchInReverse"],type:"checkbox"},{label:"Search Requests Every (s)",path:["EntrySearch","SearchRequestsEvery"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<1)return"Search Requests Every must be at least 1 second."}},{label:"Search Again On Completion",path:["EntrySearch","SearchAgainOnSearchCompletion"],type:"checkbox"},{label:"Use Temp Profile For Missing",path:["EntrySearch","UseTempForMissing"],type:"checkbox"},{label:"Keep Temp Profile",path:["EntrySearch","KeepTempProfile"],type:"checkbox"},{label:"Force Reset Temp Profiles",path:["EntrySearch","ForceResetTempProfiles"],type:"checkbox",description:"Reset all items using temp profiles to their original main profile on qBitrr startup"},{label:"Temp Profile Reset Timeout (Minutes)",path:["EntrySearch","TempProfileResetTimeoutMinutes"],type:"number",description:"Timeout in minutes after which items with temp profiles are automatically reset to main profile (0 = disabled)"},{label:"Profile Switch Retry Attempts",path:["EntrySearch","ProfileSwitchRetryAttempts"],type:"number",description:"Number of retry attempts for profile switch API calls (default: 3)"},{label:"Search By Series",path:["EntrySearch","SearchBySeries"],type:"select",options:["smart","true","false"],description:"smart = auto (series search for multiple episodes, episode search for single), true = always series search, false = always episode search",format:e=>typeof e=="boolean"?e?"true":"false":String(e||"smart"),parse:e=>{const t=String(e);return t==="true"||t==="false"?t:"smart"}},{label:"Prioritize Today's Releases",path:["EntrySearch","PrioritizeTodaysReleases"],type:"checkbox"}],es=[{label:"Search Ombi Requests",path:["EntrySearch","Ombi","SearchOmbiRequests"],type:"checkbox"},{label:"Ombi URI",path:["EntrySearch","Ombi","OmbiURI"],type:"text",placeholder:"http://host:port"},{label:"Ombi API Key",path:["EntrySearch","Ombi","OmbiAPIKey"],type:"password"},{label:"Approved Only",path:["EntrySearch","Ombi","ApprovedOnly"],type:"checkbox"},{label:"Is 4K Instance",path:["EntrySearch","Ombi","Is4K"],type:"checkbox"}],ts=[{label:"Search Overseerr Requests",path:["EntrySearch","Overseerr","SearchOverseerrRequests"],type:"checkbox"},{label:"Overseerr URI",path:["EntrySearch","Overseerr","OverseerrURI"],type:"text",placeholder:"http://host:port"},{label:"Overseerr API Key",path:["EntrySearch","Overseerr","OverseerrAPIKey"],type:"password"},{label:"Approved Only",path:["EntrySearch","Overseerr","ApprovedOnly"],type:"checkbox"},{label:"Is 4K Instance",path:["EntrySearch","Overseerr","Is4K"],type:"checkbox"}],rs=[{label:"Case Sensitive Matches",path:["Torrent","CaseSensitiveMatches"],type:"checkbox"},{label:"Folder Exclusion Regex",path:["Torrent","FolderExclusionRegex"],type:"text",parse:Q,format:Y},{label:"File Name Exclusion Regex",path:["Torrent","FileNameExclusionRegex"],type:"text",parse:Q,format:Y},{label:"File Extension Allowlist",path:["Torrent","FileExtensionAllowlist"],type:"text",parse:Q,format:Y},{label:"Auto Delete",path:["Torrent","AutoDelete"],type:"checkbox"},{label:"Ignore Torrents Younger Than (s)",path:["Torrent","IgnoreTorrentsYoungerThan"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Ignore Torrents Younger Than must be a non-negative number."}},{label:"Maximum ETA (s)",path:["Torrent","MaximumETA"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Maximum ETA must be -1 or a non-negative number."}},{label:"Maximum Deletable Percentage",path:["Torrent","MaximumDeletablePercentage"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0||t>100)return"Maximum Deletable Percentage must be between 0 and 100."}},{label:"Do Not Remove Slow",path:["Torrent","DoNotRemoveSlow"],type:"checkbox"},{label:"Stalled Delay (min)",path:["Torrent","StalledDelay"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Stalled Delay must be a non-negative number."}},{label:"Re-search Stalled",path:["Torrent","ReSearchStalled"],type:"checkbox"}],ns=[{label:"Download Rate Limit Per Torrent",path:["Torrent","SeedingMode","DownloadRateLimitPerTorrent"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Download Rate Limit must be -1 or greater."}},{label:"Upload Rate Limit Per Torrent",path:["Torrent","SeedingMode","UploadRateLimitPerTorrent"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Upload Rate Limit must be -1 or greater."}},{label:"Max Upload Ratio",path:["Torrent","SeedingMode","MaxUploadRatio"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Upload Ratio must be -1 or greater."}},{label:"Max Seeding Time (s)",path:["Torrent","SeedingMode","MaxSeedingTime"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Seeding Time must be -1 or greater."}},{label:"Remove Torrent (policy)",path:["Torrent","SeedingMode","RemoveTorrent"],type:"select",options:$e,parse:e=>{const r=String(e).match(/\((-?\d+)\)/);return r?Number(r[1]):-1},format:e=>{const t=typeof e=="number"?e:Number(e??-1);return $e.find(r=>r.includes(`(${t})`))||$e[0]}},{label:"Remove Dead Trackers",path:["Torrent","SeedingMode","RemoveDeadTrackers"],type:"checkbox"},{label:"Remove Tracker Messages",path:["Torrent","SeedingMode","RemoveTrackerWithMessage"],type:"text",parse:Q,format:Y,fullWidth:!0}],ss=[{label:"Name",path:["Name"],type:"text",required:!0},{label:"URI",path:["URI"],type:"text",required:!0},{label:"Priority",path:["Priority"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<0)return"Priority must be a non-negative number."}},{label:"Maximum ETA",path:["MaximumETA"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Maximum ETA must be -1 or a non-negative number."}},{label:"Download Rate Limit",path:["DownloadRateLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Download Rate Limit must be -1 or greater."}},{label:"Upload Rate Limit",path:["UploadRateLimit"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Upload Rate Limit must be -1 or greater."}},{label:"Max Upload Ratio",path:["MaxUploadRatio"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Upload Ratio must be -1 or greater."}},{label:"Max Seeding Time",path:["MaxSeedingTime"],type:"number",validate:e=>{const t=typeof e=="number"?e:Number(e);if(!Number.isFinite(t)||t<-1)return"Max Seeding Time must be -1 or greater."}},{label:"Add Tracker If Missing",path:["AddTrackerIfMissing"],type:"checkbox"},{label:"Remove If Exists",path:["RemoveIfExists"],type:"checkbox"},{label:"Super Seed Mode",path:["SuperSeedMode"],type:"checkbox"},{label:"Add Tags",path:["AddTags"],type:"text",parse:Q,format:Y}];function Xt(e){const t=e.toLowerCase(),r=t.includes("sonarr"),s=t.includes("lidarr"),a=[...Jn],i=Zn.filter(d=>{if(!d.path)return!0;const N=d.path.join(".");return!(!r&&(N==="EntrySearch.AlsoSearchSpecials"||N==="EntrySearch.SearchBySeries"||N==="EntrySearch.PrioritizeTodaysReleases")||s&&N==="EntrySearch.SearchByYear")}),o=s?[]:[...es],c=s?[]:[...ts],h=[...rs],x=[...ns],p=[...ss];return{generalFields:a,entryFields:i,entryOmbiFields:o,entryOverseerrFields:c,torrentFields:h,seedingFields:x,trackerFields:p}}function Nt(e){return e==null||typeof e=="string"&&e.trim()===""||Array.isArray(e)&&e.length===0}function is(e,t){const r=e.label,s=e.required??(e.type==="number"||e.type==="select");switch(e.type){case"text":case"password":return s&&Nt(t)?`${r} is required.`:void 0;case"number":{if(t==null||t==="")return s?`${r} is required.`:void 0;const a=typeof t=="number"?t:Number(t);return Number.isFinite(a)?void 0:`${r} must be a valid number.`}case"checkbox":return t==null?s?`${r} is required.`:void 0:typeof t!="boolean"?`${r} must be true or false.`:void 0;case"select":return Nt(t)?`${r} is required.`:typeof t!="string"?`${r} must be selected.`:e.options&&!e.options.includes(t)?`${r} must be one of ${e.options.join(", ")}.`:void 0;default:return}}function K(e,t,r,s,a){if(r)for(const i of t){if(i.sectionName)continue;const o=i.path??[],c=o.length?k(r,o):void 0,h=[...s,...o],x=is(i,c);if(x){e.push({path:h,message:x});continue}if(i.validate){const p=i.validate(c,a);p&&e.push({path:h,message:p})}}}function as(e){if(!e)return[];const t=[],r={root:e};K(t,Vt,e,[],r),K(t,Qt,e,[],r);for(const[s,a]of Object.entries(e))if(lt.test(s)&&a&&typeof a=="object"){const i=a;K(t,Yt,i,[s],{root:e,section:i,sectionKey:s})}else if(ot.test(s)&&a&&typeof a=="object"){const i=a,o={root:e,section:i,sectionKey:s},c=Xt(s);K(t,c.generalFields,i,[s],o),K(t,c.entryFields,i,[s],o),K(t,c.entryOmbiFields,i,[s],o),K(t,c.entryOverseerrFields,i,[s],o),K(t,c.torrentFields,i,[s],o),K(t,c.seedingFields,i,[s],o)}return t}function k(e,t){if(e)return Gt(e,t)}function os(e,t,r){Vn(e,t,r)}function ae(e,t=[]){const r={};for(const[s,a]of Object.entries(e)){const i=[...t,s];a&&typeof a=="object"&&!Array.isArray(a)?Object.assign(r,ae(a,i)):r[i.join(".")]=a}return r}function ls(e){const t=e.toLowerCase(),r=t.includes("sonarr"),s=t.includes("radarr"),a=t.includes("lidarr"),i=s?["Not a preferred word upgrade for existing movie file(s)","Not an upgrade for existing movie file(s)","Unable to determine if file is a sample"]:a?["Not a preferred word upgrade for existing album file(s)","Not an upgrade for existing album file(s)","Unable to determine if file is a sample"]:["Not a preferred word upgrade for existing episode file(s)","Not an upgrade for existing episode file(s)","Unable to determine if file is a sample"],o={SearchMissing:!0,Unmonitored:!1,SearchLimit:5,SearchByYear:!0,SearchInReverse:!1,SearchRequestsEvery:300,DoUpgradeSearch:!1,QualityUnmetSearch:!1,CustomFormatUnmetSearch:!1,ForceMinimumCustomFormat:!1,SearchAgainOnSearchCompletion:!0,UseTempForMissing:!1,KeepTempProfile:!1,ForceResetTempProfiles:!1,TempProfileResetTimeoutMinutes:0,ProfileSwitchRetryAttempts:3,QualityProfileMappings:{}};return r&&(o.AlsoSearchSpecials=!1,o.SearchBySeries="smart",o.PrioritizeTodaysReleases=!0),o.Ombi={SearchOmbiRequests:!1,OmbiURI:"CHANGE_ME",OmbiAPIKey:"CHANGE_ME",ApprovedOnly:!0},o.Overseerr={SearchOverseerrRequests:!1,OverseerrURI:"CHANGE_ME",OverseerrAPIKey:"CHANGE_ME",ApprovedOnly:!0,Is4K:!1},{Managed:!0,URI:"CHANGE_ME",APIKey:"CHANGE_ME",Category:e,ReSearch:!0,importMode:"Auto",RssSyncTimer:5,RefreshDownloadsTimer:5,ArrErrorCodesToBlocklist:i,EntrySearch:o,Torrent:{CaseSensitiveMatches:!1,FolderExclusionRegex:["\\bextras?\\b","\\bfeaturettes?\\b","\\bsamples?\\b","\\bscreens?\\b","\\bnc(ed|op)?(\\\\d+)?\\b"],FileNameExclusionRegex:["\\bncop\\\\d+?\\b","\\bnced\\\\d+?\\b","\\bsample\\b","brarbg.com\\b","\\btrailer\\b","music video","comandotorrents.com"],FileExtensionAllowlist:a?[".mp3",".flac",".m4a",".aac",".ogg",".opus",".wav",".ape",".wma",".!qB",".parts",".log",".cue"]:[".mp4",".mkv",".sub",".ass",".srt",".!qB",".parts"],AutoDelete:!1,IgnoreTorrentsYoungerThan:600,MaximumETA:604800,MaximumDeletablePercentage:.99,DoNotRemoveSlow:!0,StalledDelay:15,ReSearchStalled:!1,RemoveDeadTrackers:!1,RemoveTrackerWithMessage:["skipping tracker announce (unreachable)","No such host is known","unsupported URL protocol","info hash is not authorized with this tracker"],SeedingMode:{DownloadRateLimitPerTorrent:-1,UploadRateLimitPerTorrent:-1,MaxUploadRatio:-1,MaxSeedingTime:-1,RemoveTorrent:-1}}}}function gs(e){const{onDirtyChange:t}=e??{},{push:r}=It(),[s,a]=_.useState(null),[i,o]=_.useState(null),[c,h]=_.useState(!1),[x,p]=_.useState(!1),d=_.useCallback(async()=>{h(!0);try{const l=await sr();a(l),o(l?JSON.parse(JSON.stringify(l)):null)}catch(l){r(l instanceof Error?l.message:"Failed to load configuration","error")}finally{h(!1)}},[r]);_.useEffect(()=>{d()},[d]);const N=_.useCallback((l,u,f)=>{if(!i)return;const g=u.parse?.(f)??(u.type==="number"?Number(f)||0:u.type==="checkbox"?!!f:f);o(V(i,R=>{os(R,l,g)}))},[i]),v=_.useMemo(()=>i?Object.entries(i).filter(([l,u])=>ot.test(l)&&u&&typeof u=="object"):[],[i]),E=_.useMemo(()=>i?Object.entries(i).filter(([l,u])=>lt.test(l)&&u&&typeof u=="object"):[],[i]),C=_.useMemo(()=>{const l=[],u=[...v].sort((O,W)=>O[0].localeCompare(W[0],void 0,{numeric:!0,sensitivity:"base"})),f=[],g=[],R=[],A=[];for(const O of u){const[W]=O,M=W.toLowerCase();M.startsWith("radarr")?f.push(O):M.startsWith("sonarr")?g.push(O):M.startsWith("lidarr")?R.push(O):A.push(O)}return l.push({label:"Radarr Instances",type:"radarr",items:f}),l.push({label:"Sonarr Instances",type:"sonarr",items:g}),l.push({label:"Lidarr Instances",type:"lidarr",items:R}),A.length&&l.push({label:"Other Instances",type:"other",items:A}),l},[v]),[j,T]=_.useState(null),[b,w]=_.useState(null),[S,m]=_.useState(!1),[y,P]=_.useState(!1),[F,U]=_.useState(!1);_.useEffect(()=>{if(!i||!s){U(!1);return}const l=ae(s),u=ae(i),f=new Set(["WebUI.LiveArr","WebUI.GroupSonarr","WebUI.GroupLidarr","WebUI.Theme"]);let g=!1;for(const[R,A]of Object.entries(u)){if(f.has(R))continue;const O=l[R];if(!St(A,O)){g=!0;break}}if(!g){for(const R of Object.keys(l))if(!f.has(R)&&!(R in u)){g=!0;break}}U(g)},[i,s]),_.useEffect(()=>{t?.(F)},[F,t]),_.useEffect(()=>{if(!F)return;const l=u=>{u.preventDefault(),u.returnValue=""};return window.addEventListener("beforeunload",l),()=>{window.removeEventListener("beforeunload",l)}},[F]),_.useEffect(()=>()=>{t?.(!1)},[t]),_.useEffect(()=>{if(!!!(j||b||S||y))return;const u=R=>{R.key==="Escape"&&(T(null),w(null),m(!1),P(!1))};window.addEventListener("keydown",u);const{style:f}=document.body,g=f.overflow;return f.overflow="hidden",()=>{window.removeEventListener("keydown",u),f.overflow=g}},[j,b,S,y]),_.useEffect(()=>{j&&(v.some(([l])=>l===j)||T(null))},[j,v]);const fe=_.useCallback(l=>{if(!i)return;const u=l.charAt(0).toUpperCase()+l.slice(1);let f=1,g=`${u}-${f}`;for(;i[g];)f+=1,g=`${u}-${f}`;const R=ls(l);R&&typeof R=="object"&&(R.Name=g),o(V(i,A=>{A[g]=R})),T(g)},[i]),Jt=_.useCallback(l=>{if(!i)return;const u=l.toLowerCase();!u.startsWith("radarr")&&!u.startsWith("sonarr")&&!u.startsWith("lidarr")||!window.confirm(`Delete ${l}? This action cannot be undone.`)||l in i&&(o(V(i,g=>{delete g[l]})),j===l&&T(null),r(`${l} removed`,"success"))},[i,j,r]),Zt=_.useCallback(()=>{if(!i)return;let l=1,u=`qBit-${l}`;for(;i[u];)l+=1,u=`qBit-${l}`;const f={Disabled:!1,Host:"localhost",Port:8080,UserName:"",Password:""};o(V(i,g=>{g[u]=f})),w(u)},[i]),er=_.useCallback(l=>{if(!i)return;if(l==="qBit"){r("Cannot delete the default qBit instance","error");return}window.confirm(`Delete ${l}? This action cannot be undone.`)&&l in i&&(o(V(i,f=>{delete f[l]})),b===l&&w(null),r(`${l} removed`,"success"))},[i,b,r]),tr=_.useCallback((l,u)=>{if(!i)return;const f=u.trim();if(!(!f||f===l)){if(i[f]){r(`An instance named "${f}" already exists`,"error");return}o(V(i,g=>{const R=g[l];delete g[l],g[f]=R,R&&typeof R=="object"&&(R.Name=f)})),j===l&&T(f)}},[i,r,j]),rr=_.useCallback((l,u)=>{if(!i)return;const f=u.trim();if(!(!f||f===l)){if(l==="qBit"&&f!=="qBit"){r("Cannot rename the default qBit instance. Create a new instance instead.","error");return}if(i[f]){r(`An instance named "${f}" already exists`,"error");return}o(V(i,g=>{const R=g[l];delete g[l],g[f]=R})),b===l&&w(f)}},[i,r,b]),nr=_.useCallback(async()=>{if(i){p(!0);try{const l=as(i);if(l.length){const M=l.map(he=>`${he.path.join(".")}: ${he.message}`).join(`
|
|
2
|
+
`),ee=l.length===1?M:`Please resolve the following issues:
|
|
3
|
+
${M}`;r(ee,"error"),p(!1);return}const u=ae(s??{}),f=ae(i),g={};for(const[M,ee]of Object.entries(f)){const he=u[M];St(ee,he)||(g[M]=ee)}for(const M of Object.keys(u))M in f||(g[M]=null);if(Object.keys(g).length===0){r("No changes detected","info"),p(!1);return}const{configReloaded:R,reloadType:A,affectedInstances:O}=await ir({changes:g});let W="Configuration saved";if(A==="full"?W+=" • All instances reloaded":A==="multi_arr"&&O?.length?W+=` • Reloaded ${O.length} instances: ${O.join(", ")}`:A==="single_arr"&&O?.length?W+=` • Reloaded: ${O.join(", ")}`:A==="webui"?W+=" • WebUI restarting...":A==="frontend"&&(W+=" • Theme/display settings updated"),r(W,"success"),R&&"caches"in window)try{const M=await caches.keys();await Promise.all(M.map(ee=>caches.delete(ee)))}catch(M){console.warn("Failed to clear caches:",M)}await d()}catch(l){r(l instanceof Error?l.message:"Failed to update configuration","error")}finally{p(!1)}}},[i,s,d,r]);return c||!i?n.jsxs("section",{className:"card",children:[n.jsx("div",{className:"card-header",children:"Config"}),n.jsx("div",{className:"card-body",children:n.jsxs("div",{className:"loading",children:[n.jsx("span",{className:"spinner"})," Loading configuration…"]})})]}):n.jsxs(n.Fragment,{children:[n.jsxs("section",{className:"card",children:[n.jsx("div",{className:"card-header",children:"Config"}),n.jsxs("div",{className:"card-body config-layout",children:[n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsx("summary",{children:n.jsx("span",{children:"Core Configuration"})}),n.jsxs("div",{className:"config-grid",children:[n.jsx(Et,{title:"Settings",description:"Core application configuration",onConfigure:()=>m(!0)}),n.jsx(Et,{title:"Web Settings",description:"Web UI configuration",onConfigure:()=>P(!0)})]})]})}),n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsxs("summary",{children:[n.jsx("span",{children:"qBittorrent Instances"}),n.jsx("span",{className:"config-arr-group__count",children:E.length}),n.jsxs("button",{className:"btn small",type:"button",onClick:Zt,children:[n.jsx(I,{src:je}),"Add Instance"]})]}),n.jsx("div",{className:"config-arr-grid",children:E.map(([l,u])=>{const f=k(u,["Host"]),g=k(u,["Port"]),R=k(u,["Disabled"]),A=l==="qBit";return n.jsxs("div",{className:"card config-card config-arr-card",children:[n.jsxs("div",{className:"card-header",children:[l,A&&n.jsx("span",{style:{marginLeft:"8px",opacity:.6},children:"(Default)"})]}),n.jsxs("div",{className:"card-body",children:[n.jsxs("dl",{className:"config-arr-summary",children:[n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Status"}),n.jsx("dd",{children:R?"Disabled":"Enabled"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Host"}),n.jsx("dd",{children:f?`${String(f)}:${g??8080}`:"-"})]})]}),n.jsxs("div",{className:"config-arr-actions",children:[A?null:n.jsxs("button",{className:"btn danger",type:"button",onClick:()=>er(l),children:[n.jsx(I,{src:Te}),"Delete"]}),n.jsxs("button",{className:"btn primary",type:"button",onClick:()=>w(l),children:[n.jsx(I,{src:We}),"Configure"]})]})]})]},l)})})]})}),C.length?n.jsx("div",{className:"config-arr-groups",children:C.map(l=>n.jsx("section",{className:"config-arr-group",children:n.jsxs("details",{className:"config-arr-group__details",open:!0,children:[n.jsxs("summary",{children:[n.jsx("span",{children:l.label}),n.jsx("span",{className:"config-arr-group__count",children:l.items.length}),(l.type==="radarr"||l.type==="sonarr"||l.type==="lidarr")&&n.jsxs("button",{className:"btn small",type:"button",onClick:()=>fe(l.type),children:[n.jsx(I,{src:je}),"Add Instance"]})]}),n.jsx("div",{className:"config-arr-grid",children:l.items.map(([u,f])=>{const g=k(f,["URI"]),R=k(f,["Category"]),A=k(f,["Managed"]),O=l.type==="radarr"||l.type==="sonarr"||l.type==="lidarr";return n.jsxs("div",{className:"card config-card config-arr-card",children:[n.jsx("div",{className:"card-header",children:u}),n.jsxs("div",{className:"card-body",children:[n.jsxs("dl",{className:"config-arr-summary",children:[n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Managed"}),n.jsx("dd",{children:A?"Enabled":"Disabled"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"Category"}),n.jsx("dd",{children:R?String(R):"-"})]}),n.jsxs("div",{className:"config-arr-summary__item",children:[n.jsx("dt",{children:"URI"}),n.jsx("dd",{className:"config-arr-summary__uri",children:g?String(g):"-"})]})]}),n.jsxs("div",{className:"config-arr-actions",children:[O?n.jsxs("button",{className:"btn danger",type:"button",onClick:()=>Jt(u),children:[n.jsx(I,{src:Te}),"Delete"]}):null,n.jsxs("button",{className:"btn primary",type:"button",onClick:()=>T(u),children:[n.jsx(I,{src:We}),"Configure"]})]})]})]},u)})})]})},l.type))}):null,n.jsx("div",{className:"config-footer",children:n.jsxs("button",{className:"btn primary",onClick:()=>{nr()},disabled:x,children:[n.jsx(I,{src:Me}),"Save + Live Reload"]})})]})]}),j&&i?n.jsx(fs,{keyName:j,state:i[j]??null,onChange:N,onRename:tr,onClose:()=>T(null)}):null,S?n.jsx(wt,{title:"Settings",fields:Vt,state:i,basePath:[],onChange:N,onClose:()=>m(!1)}):null,y?n.jsx(wt,{title:"Web Settings",fields:Qt,state:i,basePath:[],onChange:N,onClose:()=>P(!1),showLiveSettings:!0}):null,b&&i?n.jsx(hs,{keyName:b,state:i[b]??null,onChange:N,onRename:rr,onClose:()=>w(null)}):null]})}function Et({title:e,description:t,onConfigure:r}){return n.jsxs("div",{className:"card config-card",children:[n.jsx("div",{className:"card-header",children:e}),n.jsxs("div",{className:"card-body config-summary-card",children:[n.jsx("p",{children:t}),n.jsx("div",{className:"config-arr-actions",children:n.jsxs("button",{className:"btn primary",type:"button",onClick:r,children:[n.jsx(I,{src:We}),"Configure"]})})]})]})}function B({title:e,fields:t,state:r,basePath:s,onChange:a,onRenameSection:i,defaultOpen:o=!1,qualityProfiles:c=[],sectionKey:h}){const x=h??s[0]??"";if(e==="Quality Profile Mappings"){const d=k(r,["EntrySearch","QualityProfileMappings"])??{},N=Object.entries(d),v=!!(k(r,["URI"])&&k(r,["APIKey"])),E=c.length>0,C=()=>{const b={...d,"":""};a([...s,"EntrySearch","QualityProfileMappings"],{},b)},j=(b,w,S)=>{const m={...d};b!==w&&delete m[b],w.trim()&&(m[w.trim()]=S.trim()),a([...s,"EntrySearch","QualityProfileMappings"],{},m)},T=b=>{const w={...d};delete w[b],a([...s,"EntrySearch","QualityProfileMappings"],{},w)};return n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsxs("div",{className:"config-section__body",children:[n.jsx("div",{className:"field-description",style:{marginBottom:"1rem"},children:"Map main quality profile names to temporary profile names. Items will be downgraded to the temp profile when not found, then upgraded back to the main profile when available."}),v?E?n.jsxs(n.Fragment,{children:[n.jsx("div",{className:"profile-mappings-grid",children:N.map(([b,w],S)=>n.jsxs("div",{className:"profile-mapping-row",children:[n.jsxs("div",{className:"field",children:[n.jsx("label",{children:"Main Profile"}),n.jsx(ke,{options:c.map(m=>({value:m.name,label:m.name})),value:b?{value:b,label:b}:null,onChange:m=>j(b,m?.value||"",w),placeholder:"Select main profile...",isClearable:!0,styles:Be(),classNamePrefix:"react-select"})]}),n.jsxs("div",{className:"field",children:[n.jsx("label",{children:"Temp Profile"}),n.jsx(ke,{options:c.map(m=>({value:m.name,label:m.name})),value:w?{value:w,label:w}:null,onChange:m=>j(b,b,m?.value||""),placeholder:"Select temp profile...",isClearable:!0,styles:Be(),classNamePrefix:"react-select"})]}),n.jsx("button",{className:"btn ghost icon-only",type:"button",onClick:()=>T(b),title:"Delete mapping",children:n.jsx(I,{src:Te})})]},S))}),n.jsx("div",{className:"config-actions",children:n.jsxs("button",{className:"btn",type:"button",onClick:C,children:[n.jsx(I,{src:je}),"Add Profile Mapping"]})})]}):n.jsxs("div",{className:"alert info",children:['ℹ️ Click "Test Connection" above to load quality profiles from your ',x," instance"]}):n.jsx("div",{className:"alert warning",children:'⚠️ Please configure URI and API Key first, then click "Test Connection" to load quality profiles'})]})]})}if(e==="Trackers"){const d=k(r,["Torrent","Trackers"])??[],N=()=>{const E=[...d,{Url:"",RemoveIfExists:!1,SuperSeedMode:!1,AddTags:[]}];a([...s,"Torrent","Trackers"],{},E)},v=E=>{const C=[...d];C.splice(E,1),a([...s,"Torrent","Trackers"],{},C)};return n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsxs("div",{className:"config-section__body",children:[n.jsx("div",{className:"tracker-grid",children:d.map((E,C)=>n.jsx(cs,{fields:t,state:E,basePath:[...s,"Torrent","Trackers",String(C)],onChange:a,onDelete:()=>v(C)},C))}),n.jsx("div",{className:"config-actions",children:n.jsxs("button",{className:"btn",type:"button",onClick:N,children:[n.jsx(I,{src:je}),"Add Tracker"]})})]})]})}const p=t.map(d=>{if(d.sectionName){if(!x)return null;const y=Tt([x]);let P;return x.startsWith("Radarr")?P="Radarr":x.startsWith("Sonarr")?P="Sonarr":x.startsWith("Lidarr")&&(P="Lidarr"),n.jsx(ds,{label:d.label,tooltip:y,currentName:x,placeholder:d.placeholder,expectedPrefix:P,onRename:F=>i?.(x,F)},`${x}.__name`)}const N=d.path??[],v=[...s,...N],E=v.join("."),C=v.length>0?k(r,v):void 0,j=d.format?.(C)??(d.type==="checkbox"?!!C:String(C??"")),T=Tt(v),b=d.description??Ht(T)??(d.type==="checkbox"?`Enable or disable ${d.label}.`:`Set the ${d.label} value.`),S=s.length>0&&ot.test(s[0]??"")&&(d.path?.[d.path.length-1]??"")==="APIKey",m=d.fullWidth?"field field--full-width":"field";if(d.secure)return n.jsx(us,{label:d.label,tooltip:T,description:b,value:String(C??""),placeholder:d.placeholder,canRefresh:!S,onChange:y=>a(v,d,y)},E);if(d.type==="checkbox")return n.jsxs("div",{className:"checkbox-field",children:[n.jsxs("label",{title:T,children:[n.jsx("input",{type:"checkbox",checked:!!j,onChange:y=>a(v,d,y.target.checked)}),d.label]}),b&&n.jsx("div",{className:"field-description",children:b})]},E);if(d.type==="select"){const y=d.label==="Theme"&&v.join(".")==="WebUI.Theme";let P=j;if(y&&typeof j=="string"){const F=j.toLowerCase();F==="light"?P="Light":P="Dark"}return n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx(ke,{options:(d.options??[]).map(F=>({value:F,label:F})),value:P?{value:P,label:P}:null,onChange:F=>{const U=F?.value||"";if(a(v,d,U),y&&typeof U=="string"&&U){const fe=U.toLowerCase();document.documentElement.setAttribute("data-theme",fe),localStorage.setItem("theme",fe)}},styles:Be()}),b&&n.jsx("div",{className:"field-description",children:b}),y&&n.jsx("div",{className:"field-hint",children:"Theme changes apply immediately"})]},E)}return d.type==="number"?n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"number",value:Number(j)||0,onChange:y=>a(v,d,String(y.target.value)),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},E):d.type==="password"?n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"password",value:String(j),onChange:y=>a(v,d,y.target.value),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},E):n.jsxs("div",{className:m,children:[n.jsx("label",{title:T,children:d.label}),n.jsx("input",{type:"text",value:String(j),onChange:y=>a(v,d,y.target.value),placeholder:d.placeholder}),b&&n.jsx("div",{className:"field-description",children:b})]},E)});return e?n.jsxs("details",{className:"config-section",open:o,children:[n.jsx("summary",{children:e}),n.jsx("div",{className:"config-section__body field-grid",children:p})]}):n.jsx("div",{className:"field-grid",children:p})}function cs({fields:e,state:t,basePath:r,onChange:s,onDelete:a}){const i=k(t,["Name"])||"New Tracker";return n.jsxs("details",{className:"card tracker-card",open:!0,children:[n.jsxs("summary",{className:"card-header",children:[n.jsx("span",{children:i}),n.jsx("button",{className:"btn danger ghost",type:"button",onClick:a,children:n.jsx(I,{src:Te})})]}),n.jsx("div",{className:"card-body",children:n.jsx(B,{title:null,fields:e,state:t,basePath:r,onChange:s})})]})}function ds({label:e,currentName:t,placeholder:r,tooltip:s,expectedPrefix:a,onRename:i}){const[o,c]=_.useState(t),h=Ht(s)??`Rename the ${t} instance.`;_.useEffect(()=>{c(t)},[t]);const x=()=>{const p=o.trim();if(!p){c(t);return}let d=p;if(lt.test(t)){if(p==="qBit"?d="qBit":p.startsWith("qBit-")||(d=`qBit-${p}`),d!=="qBit"&&!d.match(/^qBit-.+$/)){alert(`qBit instance name must match format: qBit-NAME
|
|
4
4
|
Example: qBit-seedbox`),c(t);return}}else if(a&&!p.startsWith(a)&&(d=a+(p.startsWith("-")?p:`-${p}`)),!/^(Radarr|Sonarr|Lidarr)-.+$/.test(d)){alert(`Instance name must match format: ${a||"(Rad|Son|Lid)arr"}-(name)
|
|
5
|
-
Example: ${a||"Radarr"}-Movies`),c(t);return}d!==t?i(d):c(t)};return n.jsxs("div",{className:"field",children:[n.jsxs("label",{className:"field-label",children:[n.jsx("span",{children:e}),s?n.jsx("span",{className:"help-icon",title:s,"aria-label":s,children:"?"}):null]}),h?n.jsx("p",{className:"field-description",children:h}):null,n.jsx("input",{type:"text",value:o,placeholder:r,onChange:p=>c(p.target.value),onBlur:x,onKeyDown:p=>{p.key==="Enter"?(p.preventDefault(),x()):p.key==="Escape"&&(p.preventDefault(),c(t))}})]})}function
|
|
5
|
+
Example: ${a||"Radarr"}-Movies`),c(t);return}d!==t?i(d):c(t)};return n.jsxs("div",{className:"field",children:[n.jsxs("label",{className:"field-label",children:[n.jsx("span",{children:e}),s?n.jsx("span",{className:"help-icon",title:s,"aria-label":s,children:"?"}):null]}),h?n.jsx("p",{className:"field-description",children:h}):null,n.jsx("input",{type:"text",value:o,placeholder:r,onChange:p=>c(p.target.value),onBlur:x,onKeyDown:p=>{p.key==="Enter"?(p.preventDefault(),x()):p.key==="Escape"&&(p.preventDefault(),c(t))}})]})}function us({label:e,value:t,placeholder:r,tooltip:s,description:a,canRefresh:i=!0,onChange:o}){const[c,h]=_.useState(!1),x=()=>{let p="";typeof crypto<"u"&&typeof crypto.randomUUID=="function"?p=crypto.randomUUID().replace(/-/g,""):p=Array.from({length:32},()=>Math.floor(Math.random()*16).toString(16)).join(""),o(p)};return n.jsxs("div",{className:"field secure-field",children:[n.jsx("label",{title:s,children:e}),n.jsxs("div",{className:"secure-field__input-group",children:[n.jsx("input",{type:c?"text":"password",value:t,placeholder:r,onChange:p=>o(p.target.value)}),n.jsx("button",{type:"button",className:"btn ghost",onClick:()=>h(!c),children:n.jsx(I,{src:Qn})}),i&&n.jsx("button",{type:"button",className:"btn ghost",onClick:x,children:n.jsx(I,{src:Ct})})]}),a&&n.jsx("div",{className:"field-description",children:a})]})}function fs({keyName:e,state:t,onChange:r,onRename:s,onClose:a}){const{generalFields:i,entryFields:o,entryOmbiFields:c,entryOverseerrFields:h,torrentFields:x,seedingFields:p,trackerFields:d}=Xt(e),{push:N}=It(),[v,E]=_.useState({testing:!1,result:null}),[C,j]=_.useState([]),T=S=>{if(t)return Gt(t,S)};_.useEffect(()=>{E({testing:!1,result:null}),j([])},[T(["URI"]),T(["APIKey"])]),_.useEffect(()=>{const S=T(["URI"]),m=T(["APIKey"]);S&&m&&!v.testing&&!v.result&&b(!0)},[]);const b=async(S=!1)=>{const m=T(["URI"]),y=T(["APIKey"]),P=e.toLowerCase(),F=P.includes("radarr")?"radarr":P.includes("sonarr")?"sonarr":"lidarr";if(!m||!y)return S||N("Please configure URI and API Key first","error"),!1;E({testing:!0,result:null});try{const U=await ar({arrType:F,uri:m,apiKey:y});return E({testing:!1,result:U}),U.success?(U.qualityProfiles&&j(U.qualityProfiles),S||N(`Connected to ${e} successfully!`,"success"),!0):(S||N(`Connection failed: ${U.message}`,"error"),!1)}catch{return E({testing:!1,result:null}),S||N("Test connection failed","error"),!1}},w=async()=>{const S=T(["URI"]),m=T(["APIKey"]);S&&m?await b(!1)&&(N("Configuration saved successfully","success"),a()):a()};return n.jsx("div",{className:"modal-backdrop",role:"presentation",onClick:a,children:n.jsxs("div",{className:"modal",role:"dialog","aria-modal":"true","aria-labelledby":"arr-instance-modal-title",onClick:S=>S.stopPropagation(),children:[n.jsxs("div",{className:"modal-header",children:[n.jsxs("h2",{id:"arr-instance-modal-title",children:["Configure ",n.jsx("code",{children:e})]}),n.jsxs("button",{className:"btn ghost",type:"button",onClick:a,children:[n.jsx(I,{src:Je}),"Close"]})]}),n.jsxs("div",{className:"modal-body",children:[n.jsx(B,{title:null,fields:i,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),onRenameSection:s,sectionKey:e,defaultOpen:!0}),v.result&&n.jsx("div",{className:`alert ${v.result.success?"success":"error"}`,style:{margin:"16px 0"},children:v.result.success?n.jsxs(n.Fragment,{children:[n.jsxs("strong",{children:["✓ ",v.result.message]}),v.result.systemInfo&&n.jsxs("div",{className:"alert-details",children:["Version: ",v.result.systemInfo.version,v.result.systemInfo.branch&&` (${v.result.systemInfo.branch})`]}),v.result.qualityProfiles&&n.jsxs("div",{className:"alert-details",children:["Found ",v.result.qualityProfiles.length," quality profile(s)"]})]}):n.jsxs(n.Fragment,{children:[n.jsx("strong",{children:"⚠️ Connection Failed"}),n.jsx("br",{}),v.result.message]})}),n.jsx(B,{title:"Entry Search",fields:o,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e,defaultOpen:!0}),n.jsx(B,{title:"Quality Profile Mappings",fields:[],state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e,defaultOpen:!0,qualityProfiles:C}),c.length>0&&n.jsx(B,{title:"Ombi Integration",fields:c,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e}),h.length>0&&n.jsx(B,{title:"Overseerr Integration",fields:h,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e}),n.jsx(B,{title:"Torrent Handling",fields:x,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e}),n.jsx(B,{title:"Seeding",fields:p,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e}),n.jsx(B,{title:"Trackers",fields:d,state:t,basePath:[],onChange:(S,m,y)=>r([e,...S],m,y),sectionKey:e})]}),n.jsxs("div",{className:"modal-footer",children:[n.jsx("button",{className:"btn secondary",type:"button",onClick:()=>b(!1),disabled:v.testing,children:v.testing?n.jsxs(n.Fragment,{children:[n.jsx(I,{src:Ct}),"Testing..."]}):"Test"}),n.jsxs("button",{className:"btn primary",type:"button",onClick:w,children:[n.jsx(I,{src:Me}),"Save"]})]})]})})}function hs({keyName:e,state:t,onChange:r,onRename:s,onClose:a}){const i=e==="qBit";return n.jsx("div",{className:"modal-backdrop",role:"presentation",onClick:a,children:n.jsxs("div",{className:"modal",role:"dialog","aria-modal":"true","aria-labelledby":"qbit-instance-modal-title",onClick:o=>o.stopPropagation(),children:[n.jsxs("div",{className:"modal-header",children:[n.jsxs("h2",{id:"qbit-instance-modal-title",children:["Configure ",n.jsx("code",{children:e}),i&&n.jsx("span",{style:{marginLeft:"8px",opacity:.6},children:"(Default Instance)"})]}),n.jsxs("button",{className:"btn ghost",type:"button",onClick:a,children:[n.jsx(I,{src:Je}),"Close"]})]}),n.jsxs("div",{className:"modal-body",children:[n.jsx(B,{title:null,fields:Yt,state:t,basePath:[],onChange:(o,c,h)=>r([e,...o],c,h),onRenameSection:i?void 0:s,sectionKey:e,defaultOpen:!0}),i&&n.jsx("div",{className:"alert info",style:{marginTop:"16px"},children:'ℹ️ This is the default qBittorrent instance (required). To add additional instances, use the "Add Instance" button.'})]}),n.jsx("div",{className:"modal-footer",children:n.jsxs("button",{className:"btn primary",type:"button",onClick:a,children:[n.jsx(I,{src:Me}),"Done"]})})]})})}function wt({title:e,fields:t,state:r,basePath:s,onChange:a,onClose:i,showLiveSettings:o=!1}){const c=or();return r?n.jsx("div",{className:"modal-backdrop",role:"presentation",onClick:i,children:n.jsxs("div",{className:"modal",role:"dialog","aria-modal":"true","aria-labelledby":`${e}-modal-title`,onClick:h=>h.stopPropagation(),children:[n.jsxs("div",{className:"modal-header",children:[n.jsx("h2",{id:`${e}-modal-title`,children:e}),n.jsxs("button",{className:"btn ghost",type:"button",onClick:i,children:[n.jsx(I,{src:Je}),"Close"]})]}),n.jsxs("div",{className:"modal-body",children:[n.jsx(B,{title:null,fields:t,state:r,basePath:s,onChange:a,defaultOpen:!0}),o&&c&&n.jsxs("div",{className:"field-group",children:[n.jsx("h3",{className:"field-group-title",children:"Live Settings"}),n.jsxs("div",{className:"field-group-content",children:[n.jsxs("div",{className:"field",children:[n.jsxs("label",{children:[n.jsx("input",{type:"checkbox",checked:c.liveArr,onChange:h=>c.setLiveArr(h.target.checked)})," ","Live Arr Updates"]}),n.jsx("p",{className:"field-description",children:"Enable real-time updates for Arr views"})]}),n.jsxs("div",{className:"field",children:[n.jsxs("label",{children:[n.jsx("input",{type:"checkbox",checked:c.groupSonarr,onChange:h=>c.setGroupSonarr(h.target.checked)})," ","Group Sonarr by Series"]}),n.jsx("p",{className:"field-description",children:"Group Sonarr episodes by series in views"})]}),n.jsxs("div",{className:"field",children:[n.jsxs("label",{children:[n.jsx("input",{type:"checkbox",checked:c.groupLidarr,onChange:h=>c.setGroupLidarr(h.target.checked)})," ","Group Lidarr by Artist"]}),n.jsx("p",{className:"field-description",children:"Group Lidarr albums by artist in views"})]}),n.jsxs("div",{className:"field",children:[n.jsx("label",{children:"Theme"}),n.jsxs("select",{value:c.theme,onChange:h=>c.setTheme(h.target.value),children:[n.jsx("option",{value:"dark",children:"Dark"}),n.jsx("option",{value:"light",children:"Light"})]}),n.jsx("p",{className:"field-description",children:"WebUI theme (Light or Dark)"})]})]})]})]}),n.jsx("div",{className:"modal-footer",children:n.jsxs("button",{className:"btn primary",type:"button",onClick:i,children:[n.jsx(I,{src:Me}),"Done"]})})]})}):null}export{gs as ConfigView};
|
|
6
6
|
//# sourceMappingURL=ConfigView.js.map
|