diff --git a/Build/.eslintrc.js b/Build/.eslintrc.js
index 84aedd192d01714de89d77d82428ba60d102eced..d5b49cc7095354f2d651637776bda6c0d1cb80b1 100644
--- a/Build/.eslintrc.js
+++ b/Build/.eslintrc.js
@@ -37,6 +37,7 @@ module.exports = {
     "@typescript-eslint/no-unused-vars": "error",
     "@typescript-eslint/member-ordering": "error",
     "@typescript-eslint/prefer-readonly": "error",
+    "@typescript-eslint/prefer-string-starts-ends-with": "error",
     "@typescript-eslint/naming-convention": [
       "error",
       {
diff --git a/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-code-completion.ts b/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-code-completion.ts
index b438e57e37e09d0da94a7185690f665e7a7a9b2f..463075c943e0e892dda75372eeb3031fc64e409b 100644
--- a/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-code-completion.ts
+++ b/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-code-completion.ts
@@ -97,7 +97,7 @@ export class TsCodeCompletion {
       let childNode;
       // if the childnode has a value and there is a part of a reference operator ('<')
       // and it does not look like a html tag ('>')
-      if (childNodes[key].v && childNodes[key].v[0] === '<' && childNodes[key].v.indexOf('>') === -1) {
+      if (childNodes[key].v && childNodes[key].v.startsWith('<') && !childNodes[key].v.includes('>')) {
         const path = childNodes[key].v.replace(/</, '').trim();
         // if there are still whitespaces it's no path
         if (path.indexOf(' ') === -1) {
diff --git a/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-parser.ts b/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-parser.ts
index 9b48fd22c0db588639aaadddf7f4f2508ef65b3a..088ea398e7a65a4c4aa6ba39c36f21ef9230a4e5 100644
--- a/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-parser.ts
+++ b/Build/Sources/TypeScript/backend/code-editor/autocomplete/ts-parser.ts
@@ -191,11 +191,11 @@ export class TsParser {
         if (i < tokens.length && tokens[i].string.length > 0) {
           const tokenValue = tokens[i].string;
 
-          if (tokenValue[0] === '#') {
+          if (tokenValue.startsWith('#')) {
             stack.push('#');
           } else if (tokenValue === '(') {
             stack.push('(');
-          } else if (tokenValue[0] === '/' && tokenValue[1] === '*') {
+          } else if (tokenValue.startsWith('/*')) {
             stack.push('/*');
           } else if (tokenValue === '{') {
             // TODO: ignore whole block if wrong whitespaces in this line
@@ -237,7 +237,7 @@ export class TsParser {
           if (tokenValue === ')') {
             stack.popIfLastElementEquals('(');
           }
-          if (tokenValue[0] === '*' && tokenValue[1] === '/') {
+          if (tokenValue.startsWith('*/')) {
             stack.popIfLastElementEquals('/*');
             ignoreLine = true;
           }
diff --git a/Build/Sources/TypeScript/backend/form-engine-validation.ts b/Build/Sources/TypeScript/backend/form-engine-validation.ts
index 636b9f765e6ffe65d94ab94f132b05793ea3ae29..51eccf1fe356c65713e28250d33ff7e8627f9b9c 100644
--- a/Build/Sources/TypeScript/backend/form-engine-validation.ts
+++ b/Build/Sources/TypeScript/backend/form-engine-validation.ts
@@ -604,7 +604,7 @@ export default (function() {
   FormEngineValidation.parseDouble = function(value: number|string|boolean, precision: number = 2): string {
     let theVal = '' + value;
     theVal = theVal.replace(/[^0-9,.-]/g, '');
-    const negative = theVal.substring(0, 1) === '-';
+    const negative = theVal.startsWith('-');
     theVal = theVal.replace(/-/g, '');
     theVal = theVal.replace(/,/g, '.');
     if (theVal.indexOf('.') === -1) {
diff --git a/Build/Sources/TypeScript/rte_ckeditor/rte-link-browser.ts b/Build/Sources/TypeScript/rte_ckeditor/rte-link-browser.ts
index dc538996cf53df0335679383c63c04aca94c297c..f1e5a4f2742939f7336394f59752439b8c256879 100644
--- a/Build/Sources/TypeScript/rte_ckeditor/rte-link-browser.ts
+++ b/Build/Sources/TypeScript/rte_ckeditor/rte-link-browser.ts
@@ -92,7 +92,7 @@ class RteLinkBrowser {
       link = linkMatch[1] + linkMatch[2];
       const paramsPrefix = linkMatch[2].length > 0 ? '&' : '?';
       if (queryParams.length > 0) {
-        if (queryParams[0] === '&') {
+        if (queryParams.startsWith('&')) {
           queryParams = queryParams.substr(1);
         }
         // If params is set, append it
diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-code-completion.js b/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-code-completion.js
index f52aef629947e93323a5d92e41a0bd63531dcffc..c005e00f776b1981fe2e3357281f657e6532e4ce 100644
--- a/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-code-completion.js
+++ b/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-code-completion.js
@@ -10,4 +10,4 @@
  *
  * The TYPO3 project - inspiring people to share!
  */
-import AjaxRequest from"@typo3/core/ajax/ajax-request.js";import{TsRef}from"@typo3/backend/code-editor/autocomplete/ts-ref.js";import{TsParser}from"@typo3/backend/code-editor/autocomplete/ts-parser.js";import{CompletionResult}from"@typo3/backend/code-editor/autocomplete/completion-result.js";export class TsCodeCompletion{constructor(e){this.extTsObjTree={},this.parser=null,this.proposals=null,this.compResult=null,this.tsRef=new TsRef,this.parser=new TsParser(this.tsRef,this.extTsObjTree),this.tsRef.loadTsrefAsync(),this.loadExtTemplatesAsync(e)}refreshCodeCompletion(e){const t=this.getFilter(e),s=this.parser.buildTsObjTree(e);this.compResult=new CompletionResult(this.tsRef,s),this.proposals=this.compResult.getFilteredProposals(t);const r=[];for(let e=0;e<this.proposals.length;e++)r[e]=this.proposals[e].word;return r}loadExtTemplatesAsync(e){if(Number.isNaN(e)||0===e)return null;new AjaxRequest(TYPO3.settings.ajaxUrls.codeeditor_codecompletion_loadtemplates).withQueryArguments({pageId:e}).get().then((async e=>{this.extTsObjTree.c=await e.resolve(),this.resolveExtReferencesRec(this.extTsObjTree.c)}))}resolveExtReferencesRec(e){for(const t of Object.keys(e)){let s;if(e[t].v&&"<"===e[t].v[0]&&-1===e[t].v.indexOf(">")){const r=e[t].v.replace(/</,"").trim();-1===r.indexOf(" ")&&(s=this.getExtChildNode(r),null!==s&&(e[t]=s))}!s&&e[t].c&&this.resolveExtReferencesRec(e[t].c)}}getExtChildNode(e){let t=this.extTsObjTree;const s=e.split(".");for(let e=0;e<s.length;e++){const r=s[e];if(void 0===t.c||void 0===t.c[r])return null;t=t.c[r]}return t}getFilter(e){return e.completingAfterDot?"":e.token.string.replace(".","").replace(/\s/g,"")}}
\ No newline at end of file
+import AjaxRequest from"@typo3/core/ajax/ajax-request.js";import{TsRef}from"@typo3/backend/code-editor/autocomplete/ts-ref.js";import{TsParser}from"@typo3/backend/code-editor/autocomplete/ts-parser.js";import{CompletionResult}from"@typo3/backend/code-editor/autocomplete/completion-result.js";export class TsCodeCompletion{constructor(e){this.extTsObjTree={},this.parser=null,this.proposals=null,this.compResult=null,this.tsRef=new TsRef,this.parser=new TsParser(this.tsRef,this.extTsObjTree),this.tsRef.loadTsrefAsync(),this.loadExtTemplatesAsync(e)}refreshCodeCompletion(e){const t=this.getFilter(e),s=this.parser.buildTsObjTree(e);this.compResult=new CompletionResult(this.tsRef,s),this.proposals=this.compResult.getFilteredProposals(t);const r=[];for(let e=0;e<this.proposals.length;e++)r[e]=this.proposals[e].word;return r}loadExtTemplatesAsync(e){if(Number.isNaN(e)||0===e)return null;new AjaxRequest(TYPO3.settings.ajaxUrls.codeeditor_codecompletion_loadtemplates).withQueryArguments({pageId:e}).get().then((async e=>{this.extTsObjTree.c=await e.resolve(),this.resolveExtReferencesRec(this.extTsObjTree.c)}))}resolveExtReferencesRec(e){for(const t of Object.keys(e)){let s;if(e[t].v&&e[t].v.startsWith("<")&&!e[t].v.includes(">")){const r=e[t].v.replace(/</,"").trim();-1===r.indexOf(" ")&&(s=this.getExtChildNode(r),null!==s&&(e[t]=s))}!s&&e[t].c&&this.resolveExtReferencesRec(e[t].c)}}getExtChildNode(e){let t=this.extTsObjTree;const s=e.split(".");for(let e=0;e<s.length;e++){const r=s[e];if(void 0===t.c||void 0===t.c[r])return null;t=t.c[r]}return t}getFilter(e){return e.completingAfterDot?"":e.token.string.replace(".","").replace(/\s/g,"")}}
\ No newline at end of file
diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-parser.js b/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-parser.js
index 35ffbc492a527fbb29c02434283c1a9674ec9f2c..6959aba6eb1e52f17a703b3f945ddfd9cfb83f40 100644
--- a/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-parser.js
+++ b/typo3/sysext/backend/Resources/Public/JavaScript/code-editor/autocomplete/ts-parser.js
@@ -10,4 +10,4 @@
  *
  * The TYPO3 project - inspiring people to share!
  */
-export class TreeNode{constructor(e,t){this.childNodes={},this.extPath="",this.parent=null,this.name=e,this.childNodes={},this.extPath="",this.value="",this.isExternal=!1,this.tsParser=t}getChildNodes(){const e=this.getExtNode();if(null!==e&&"object"==typeof e.c)for(const t of Object.keys(e.c)){const s=new TreeNode(t,this.tsParser);s.global=!0,s.value=e.c[t].v?e.c[t].v:"",s.isExternal=!0,this.childNodes[t]=s}return this.childNodes}getValue(){if(this.value)return this.value;const e=this.getExtNode();if(e&&e.v)return e.v;const t=this.getNodeTypeFromTsref();return t||""}getNodeTypeFromTsref(){const e=this.extPath.split(".").pop(),t=this.parent.getValue();if(t&&this.tsParser.tsRef.typeHasProperty(t,e)){return this.tsParser.tsRef.getType(t).properties[e].value}return""}getExtNode(){let e=this.tsParser.extTsObjTree;if(""===this.extPath)return e;const t=this.extPath.split(".");for(let s=0;s<t.length;s++){const l=t[s];if(void 0===e.c||void 0===e.c[l])return null;e=e.c[l]}return e}}class Stack extends Array{lastElementEquals(e){return this.length>0&&this[this.length-1]===e}popIfLastElementEquals(e){return!!this.lastElementEquals(e)&&(this.pop(),!0)}}export class TsParser{constructor(e,t){this.tsRef=e,this.extTsObjTree=t,this.tsTree=new TreeNode("_L_",this)}getOperator(e){const t=[":=","=<","<",">","="];for(let s=0;s<t.length;s++){const l=t[s];if(-1!==e.indexOf(l))return("=<"===l||"<"===l)&&e.indexOf(">")>-1?"=":l}return-1}buildTsObjTree(e){this.tsTree=new TreeNode("",this),this.tsTree.value="TLO";let t=1,s="",l=!1,r=!1;const n=new Stack,i=[];let a;for(;t<=e.currentLineNumber;){s="";const h=e.lineTokens[t-1];for(let e=0;e<=h.length;++e)if(e<h.length&&h[e].string.length>0){const t=h[e].string;if("#"===t[0]?n.push("#"):"("===t?n.push("("):"/"===t[0]&&"*"===t[1]?n.push("/*"):"{"===t&&-1===this.getOperator(s)&&(n.push("{"),i.push(s.trim()),l=!0),-1===t.search(/^\s*\[.*\]/)||-1!==s.search(/\S/)||-1!==t.search(/^\s*\[(global|end|GLOBAL|END)\]/)||n.lastElementEquals("#")||n.lastElementEquals("/*")||n.lastElementEquals("{")||n.lastElementEquals("(")||(r=!0,l=!0),-1!==s.search(/\S/)||n.lastElementEquals("#")||n.lastElementEquals("/*")||n.lastElementEquals("(")||(-1===t.search(/^\s*\[(global|end|GLOBAL|END)\]/)||n.lastElementEquals("{"))&&-1===t.search(/^\s*\[(global|GLOBAL)\]/)||(r=!1,l=!0),")"===t&&n.popIfLastElementEquals("("),"*"===t[0]&&"/"===t[1]&&(n.popIfLastElementEquals("/*"),l=!0),"}"===t){""===s.replace(/\s/g,"")&&(n.popIfLastElementEquals("{"),i.length>0&&i.pop(),l=!0)}n.lastElementEquals("#")||(s+=t)}else{if(!(n.lastElementEquals("/*")||n.lastElementEquals("(")||l||r)){s=s.trim();const e=this.getOperator(s);if(-1!==e){const t=s.indexOf(e);a=s.substring(0,t),i.length>0&&(a=i.join(".")+"."+a);let l=s.substring(t+e.length,s.length).trim();switch(a=a.trim(),e){case"=":-1===a.search(/\s/g)&&a.length>0&&this.setTreeNodeValue(a,l);break;case"=<":i.length>0&&"."===l.substr(0,1)&&(l=i.join(".")+l),-1===a.search(/\s/g)&&a.length>0&&-1===l.search(/\s/g)&&l.length>0&&this.setReference(a,l);break;case"<":i.length>0&&"."===l.substr(0,1)&&(l=i.join(".")+l),-1===a.search(/\s/g)&&a.length>0&&-1===l.search(/\s/g)&&l.length>0&&this.setCopy(a,l);break;case">":this.deleteTreeNodeValue(a)}}}n.popIfLastElementEquals("#"),l=!1}t++}if(!n.lastElementEquals("/*")&&!n.lastElementEquals("(")&&!l){const e=s.indexOf("<");-1!==e?(a=s.substring(e+1,s.length).trim(),i.length>0&&"."===a.substr(0,1)&&(a=i.join(".")+a)):(a=s,i.length>0&&(a=i.join(".")+"."+a,a=a.replace(/\s/g,"")));const t=a.lastIndexOf(".");a=a.substring(0,t)}return this.getTreeNode(a)}getTreeNode(e){if(0===(e=e.trim()).length)return this.tsTree;const t=e.split(".");let s,l=this.tsTree.childNodes,r=this.tsTree;for(let e=0;e<t.length;e++){if(s=t[e],void 0===l[s]||void 0===l[s].childNodes){l[s]=new TreeNode(s,this),l[s].parent=r;let e=r.extPath;e&&(e+="."),e+=s,l[s].extPath=e}if(e===t.length-1)return l[s];r=l[s],l=l[s].childNodes}}setTreeNodeValue(e,t){const s=this.getTreeNode(e);null!==s.parent&&"GIFBUILDER"===s.parent.value&&"TEXT"===t&&(t="GB_TEXT"),null!==s.parent&&"GIFBUILDER"===s.parent.value&&"IMAGE"===t&&(t="GB_IMAGE"),this.tsRef.isType(t)&&(s.value=t)}deleteTreeNodeValue(e){const t=this.getTreeNode(e);t.value=null,t.childNodes={}}setReference(e,t){const s=e.split("."),l=s[s.length-1],r=this.getTreeNode(e),n=this.getTreeNode(t);null!==r.parent?r.parent.childNodes[l]=n:this.tsTree.childNodes[l]=n}setCopy(e,t){this.clone=e=>{if("object"!=typeof e)return e;const t={};for(const s in e)"tsParser"!==s&&("parent"!==s?"object"==typeof e[s]?t[s]=this.clone(e[s]):t[s]=e[s]:"parent"in e&&(t.parent=e.parent));return t};const s=e.split("."),l=s[s.length-1],r=this.getTreeNode(e),n=this.getTreeNode(t);null!==r.parent?r.parent.childNodes[l]=this.clone(n):this.tsTree.childNodes[l]=this.clone(n)}}
\ No newline at end of file
+export class TreeNode{constructor(e,t){this.childNodes={},this.extPath="",this.parent=null,this.name=e,this.childNodes={},this.extPath="",this.value="",this.isExternal=!1,this.tsParser=t}getChildNodes(){const e=this.getExtNode();if(null!==e&&"object"==typeof e.c)for(const t of Object.keys(e.c)){const s=new TreeNode(t,this.tsParser);s.global=!0,s.value=e.c[t].v?e.c[t].v:"",s.isExternal=!0,this.childNodes[t]=s}return this.childNodes}getValue(){if(this.value)return this.value;const e=this.getExtNode();if(e&&e.v)return e.v;const t=this.getNodeTypeFromTsref();return t||""}getNodeTypeFromTsref(){const e=this.extPath.split(".").pop(),t=this.parent.getValue();if(t&&this.tsParser.tsRef.typeHasProperty(t,e)){return this.tsParser.tsRef.getType(t).properties[e].value}return""}getExtNode(){let e=this.tsParser.extTsObjTree;if(""===this.extPath)return e;const t=this.extPath.split(".");for(let s=0;s<t.length;s++){const l=t[s];if(void 0===e.c||void 0===e.c[l])return null;e=e.c[l]}return e}}class Stack extends Array{lastElementEquals(e){return this.length>0&&this[this.length-1]===e}popIfLastElementEquals(e){return!!this.lastElementEquals(e)&&(this.pop(),!0)}}export class TsParser{constructor(e,t){this.tsRef=e,this.extTsObjTree=t,this.tsTree=new TreeNode("_L_",this)}getOperator(e){const t=[":=","=<","<",">","="];for(let s=0;s<t.length;s++){const l=t[s];if(-1!==e.indexOf(l))return("=<"===l||"<"===l)&&e.indexOf(">")>-1?"=":l}return-1}buildTsObjTree(e){this.tsTree=new TreeNode("",this),this.tsTree.value="TLO";let t=1,s="",l=!1,r=!1;const n=new Stack,i=[];let a;for(;t<=e.currentLineNumber;){s="";const h=e.lineTokens[t-1];for(let e=0;e<=h.length;++e)if(e<h.length&&h[e].string.length>0){const t=h[e].string;if(t.startsWith("#")?n.push("#"):"("===t?n.push("("):t.startsWith("/*")?n.push("/*"):"{"===t&&-1===this.getOperator(s)&&(n.push("{"),i.push(s.trim()),l=!0),-1===t.search(/^\s*\[.*\]/)||-1!==s.search(/\S/)||-1!==t.search(/^\s*\[(global|end|GLOBAL|END)\]/)||n.lastElementEquals("#")||n.lastElementEquals("/*")||n.lastElementEquals("{")||n.lastElementEquals("(")||(r=!0,l=!0),-1!==s.search(/\S/)||n.lastElementEquals("#")||n.lastElementEquals("/*")||n.lastElementEquals("(")||(-1===t.search(/^\s*\[(global|end|GLOBAL|END)\]/)||n.lastElementEquals("{"))&&-1===t.search(/^\s*\[(global|GLOBAL)\]/)||(r=!1,l=!0),")"===t&&n.popIfLastElementEquals("("),t.startsWith("*/")&&(n.popIfLastElementEquals("/*"),l=!0),"}"===t){""===s.replace(/\s/g,"")&&(n.popIfLastElementEquals("{"),i.length>0&&i.pop(),l=!0)}n.lastElementEquals("#")||(s+=t)}else{if(!(n.lastElementEquals("/*")||n.lastElementEquals("(")||l||r)){s=s.trim();const e=this.getOperator(s);if(-1!==e){const t=s.indexOf(e);a=s.substring(0,t),i.length>0&&(a=i.join(".")+"."+a);let l=s.substring(t+e.length,s.length).trim();switch(a=a.trim(),e){case"=":-1===a.search(/\s/g)&&a.length>0&&this.setTreeNodeValue(a,l);break;case"=<":i.length>0&&"."===l.substr(0,1)&&(l=i.join(".")+l),-1===a.search(/\s/g)&&a.length>0&&-1===l.search(/\s/g)&&l.length>0&&this.setReference(a,l);break;case"<":i.length>0&&"."===l.substr(0,1)&&(l=i.join(".")+l),-1===a.search(/\s/g)&&a.length>0&&-1===l.search(/\s/g)&&l.length>0&&this.setCopy(a,l);break;case">":this.deleteTreeNodeValue(a)}}}n.popIfLastElementEquals("#"),l=!1}t++}if(!n.lastElementEquals("/*")&&!n.lastElementEquals("(")&&!l){const e=s.indexOf("<");-1!==e?(a=s.substring(e+1,s.length).trim(),i.length>0&&"."===a.substr(0,1)&&(a=i.join(".")+a)):(a=s,i.length>0&&(a=i.join(".")+"."+a,a=a.replace(/\s/g,"")));const t=a.lastIndexOf(".");a=a.substring(0,t)}return this.getTreeNode(a)}getTreeNode(e){if(0===(e=e.trim()).length)return this.tsTree;const t=e.split(".");let s,l=this.tsTree.childNodes,r=this.tsTree;for(let e=0;e<t.length;e++){if(s=t[e],void 0===l[s]||void 0===l[s].childNodes){l[s]=new TreeNode(s,this),l[s].parent=r;let e=r.extPath;e&&(e+="."),e+=s,l[s].extPath=e}if(e===t.length-1)return l[s];r=l[s],l=l[s].childNodes}}setTreeNodeValue(e,t){const s=this.getTreeNode(e);null!==s.parent&&"GIFBUILDER"===s.parent.value&&"TEXT"===t&&(t="GB_TEXT"),null!==s.parent&&"GIFBUILDER"===s.parent.value&&"IMAGE"===t&&(t="GB_IMAGE"),this.tsRef.isType(t)&&(s.value=t)}deleteTreeNodeValue(e){const t=this.getTreeNode(e);t.value=null,t.childNodes={}}setReference(e,t){const s=e.split("."),l=s[s.length-1],r=this.getTreeNode(e),n=this.getTreeNode(t);null!==r.parent?r.parent.childNodes[l]=n:this.tsTree.childNodes[l]=n}setCopy(e,t){this.clone=e=>{if("object"!=typeof e)return e;const t={};for(const s in e)"tsParser"!==s&&("parent"!==s?"object"==typeof e[s]?t[s]=this.clone(e[s]):t[s]=e[s]:"parent"in e&&(t.parent=e.parent));return t};const s=e.split("."),l=s[s.length-1],r=this.getTreeNode(e),n=this.getTreeNode(t);null!==r.parent?r.parent.childNodes[l]=this.clone(n):this.tsTree.childNodes[l]=this.clone(n)}}
\ No newline at end of file
diff --git a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine-validation.js b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine-validation.js
index 7962578445c74ca3d3dd28bb6c479d759c65434e..c86915e73975d99e1173c1684fb84026aa3b0d41 100644
--- a/typo3/sysext/backend/Resources/Public/JavaScript/form-engine-validation.js
+++ b/typo3/sysext/backend/Resources/Public/JavaScript/form-engine-validation.js
@@ -10,4 +10,4 @@
  *
  * The TYPO3 project - inspiring people to share!
  */
-import $ from"jquery";import{DateTime}from"luxon";import Md5 from"@typo3/backend/hashing/md5.js";import DocumentSaveActions from"@typo3/backend/document-save-actions.js";import Modal from"@typo3/backend/modal.js";import Severity from"@typo3/backend/severity.js";import Utility from"@typo3/backend/utility.js";import RegularEvent from"@typo3/core/event/regular-event.js";import DomHelper from"@typo3/backend/utility/dom-helper.js";import{selector}from"@typo3/core/literals.js";export default(function(){const FormEngineValidation={rulesSelector:"[data-formengine-validation-rules]",inputSelector:"[data-formengine-input-params]",markerSelector:".t3js-formengine-validation-marker",groupFieldHiddenElement:".t3js-formengine-field-group input[type=hidden]",relatedFieldSelector:"[data-relatedfieldname]",errorClass:"has-error",lastYear:0,lastDate:0,lastTime:0,passwordDummy:"********"};let formEngineFormElement;const customEvaluations=new Map;return FormEngineValidation.initialize=function(e){formEngineFormElement=e,formEngineFormElement.querySelectorAll("."+FormEngineValidation.errorClass).forEach((e=>e.classList.remove(FormEngineValidation.errorClass))),FormEngineValidation.initializeInputFields(),new RegularEvent("change",((e,n)=>{FormEngineValidation.validateField(n),FormEngineValidation.markFieldAsChanged(n)})).delegateTo(formEngineFormElement,FormEngineValidation.rulesSelector),FormEngineValidation.registerSubmitCallback();const n=new Date;FormEngineValidation.lastYear=FormEngineValidation.getYear(n),FormEngineValidation.lastDate=FormEngineValidation.getDate(n),FormEngineValidation.lastTime=0,FormEngineValidation.validate()},FormEngineValidation.initializeInputFields=function(){formEngineFormElement.querySelectorAll(FormEngineValidation.inputSelector).forEach((e=>{const n=JSON.parse(e.dataset.formengineInputParams).field,t=formEngineFormElement.querySelector(selector`[name="${n}"]`);"formengineInputInitialized"in e.dataset||(t.dataset.config=e.dataset.formengineInputParams,FormEngineValidation.initializeInputField(n))}))},FormEngineValidation.initializeInputField=function(e){const n=formEngineFormElement.querySelector(selector`[name="${e}"]`),t=formEngineFormElement.querySelector(selector`[data-formengine-input-name="${e}"]`);if(void 0!==n.dataset.config){const e=JSON.parse(n.dataset.config),a=Utility.trimExplode(",",e.evalList);let i=n.value;for(let n=0;n<a.length;n++)i=FormEngineValidation.formatValue(a[n],i,e);i.length&&(t.value=i)}new RegularEvent("change",(()=>{FormEngineValidation.updateInputField(t.dataset.formengineInputName)})).bindTo(t),t.dataset.formengineInputInitialized="true"},FormEngineValidation.registerCustomEvaluation=function(e,n){customEvaluations.has(e)||customEvaluations.set(e,n)},FormEngineValidation.formatValue=function(e,n,t){let a,i,o="";switch(e){case"date":if(n.toString().indexOf("-")>0){o=DateTime.fromISO(n.toString(),{zone:"utc"}).toFormat("dd-MM-yyyy")}else{if(""===n||"0"===n)return"";if(a=parseInt(n.toString(),10),isNaN(a))return"";i=new Date(1e3*a);o=i.getUTCDate().toString(10).padStart(2,"0")+"-"+(i.getUTCMonth()+1).toString(10).padStart(2,"0")+"-"+this.getYear(i)}break;case"datetime":if(""===n||"0"===n)return"";o=(FormEngineValidation.formatValue("time",n,t)+" "+FormEngineValidation.formatValue("date",n,t)).trim();break;case"time":case"timesec":let r;if(n.toString().indexOf("-")>0)r=DateTime.fromISO(n.toString(),{zone:"utc"});else{if(""===n||"0"===n)return"";if(a="number"==typeof n?n:parseInt(n),isNaN(a))return"";r=DateTime.fromSeconds(a,{zone:"utc"})}o="timesec"===e?r.toFormat("HH:mm:ss"):r.toFormat("HH:mm");break;case"password":o=n?FormEngineValidation.passwordDummy:"";break;default:o=n.toString()}return o},FormEngineValidation.updateInputField=function(e){const n=formEngineFormElement.querySelector(selector`[name="${e}"]`),t=formEngineFormElement.querySelector(selector`[data-formengine-input-name="${e}"]`);if(void 0!==n.dataset.config){const e=JSON.parse(n.dataset.config),a=Utility.trimExplode(",",e.evalList);let i=t.value;for(let n=0;n<a.length;n++)i=FormEngineValidation.processValue(a[n],i,e);let o=i;for(let n=0;n<a.length;n++)o=FormEngineValidation.formatValue(a[n],o,e);n.value!==i&&(n.disabled&&n.dataset.enableOnModification&&(n.disabled=!1),n.value=i,n.dispatchEvent(new Event("change")),t.value=o)}},FormEngineValidation.validateField=function(e,n){if(e instanceof $&&(console.warn("Passing a jQuery element to FormEngineValidation.validateField() is deprecated and will be removed in TYPO3 v14."),console.trace(),e=e.get(0)),!(e instanceof HTMLElement))return n;if(n=n||e.value||"",void 0===e.dataset.formengineValidationRules)return n;const t=JSON.parse(e.dataset.formengineValidationRules);let a=!1,i=0;const o=n;let r,l,s;Array.isArray(n)||(n=n.trimStart());for(const o of t){if(a)break;switch(o.type){case"required":""===n&&(a=!0,e.closest(FormEngineValidation.markerSelector).classList.add(FormEngineValidation.errorClass));break;case"range":if(""!==n){if((o.minItems||o.maxItems)&&(r=formEngineFormElement.querySelector(selector`[name="${e.dataset.relatedfieldname}"]`),i=null!==r?Utility.trimExplode(",",r.value).length:parseInt(e.value,10),void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0))),void 0!==o.lower){const e=1*o.lower;!isNaN(e)&&parseInt(n,10)<e&&(a=!0)}if(void 0!==o.upper){const e=1*o.upper;!isNaN(e)&&parseInt(n,10)>e&&(a=!0)}}break;case"select":case"category":(o.minItems||o.maxItems)&&(r=formEngineFormElement.querySelector(selector`[name="${e.dataset.relatedfieldname}"]`),i=null!==r?Utility.trimExplode(",",r.value).length:e instanceof HTMLSelectElement?e.querySelectorAll("option:checked").length:e.querySelectorAll("input[value]:checked").length,void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0)));break;case"group":case"folder":case"inline":(o.minItems||o.maxItems)&&(i=Utility.trimExplode(",",e.value).length,void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0)));break;case"min":(e instanceof HTMLInputElement||e instanceof HTMLTextAreaElement)&&e.value.length>0&&e.value.length<e.minLength&&(a=!0)}}const m=!a,d=e.closest(FormEngineValidation.markerSelector);return null!==d&&d.classList.toggle(FormEngineValidation.errorClass,!m),FormEngineValidation.markParentTab(e,m),formEngineFormElement.dispatchEvent(new CustomEvent("t3-formengine-postfieldvalidation",{cancelable:!1,bubbles:!0})),o},FormEngineValidation.processValue=function(e,n,t){let a="",i="",o=0,r=n;switch(e){case"alpha":case"num":case"alphanum":case"alphanum_x":for(a="",o=0;o<n.length;o++){const t=n.substr(o,1);let i="_"===t||"-"===t,r=t>="a"&&t<="z"||t>="A"&&t<="Z",l=t>="0"&&t<="9";switch(e){case"alphanum":i=!1;break;case"alpha":l=!1,i=!1;break;case"num":r=!1,i=!1}(r||l||i)&&(a+=t)}a!==n&&(r=a);break;case"is_in":if(t.is_in){i=""+n,t.is_in=t.is_in.replace(/[-[\]{}()*+?.,\\^$|#\s]/g,"\\$&");const e=new RegExp("[^"+t.is_in+"]+","g");a=i.replace(e,"")}else a=i;r=a;break;case"nospace":r=(""+n).replace(/ /g,"");break;case"md5":""!==n&&(r=Md5.hash(n));break;case"upper":r=n.toUpperCase();break;case"lower":r=n.toLowerCase();break;case"integer":""!==n&&(r=FormEngineValidation.parseInt(n));break;case"decimal":""!==n&&(r=FormEngineValidation.parseDouble(n));break;case"trim":r=String(n).trim();break;case"datetime":""!==n&&(r=FormEngineValidation.parseDateTime(n));break;case"date":""!==n&&(r=FormEngineValidation.parseDate(n));break;case"time":case"timesec":""!==n&&(r=FormEngineValidation.parseTime(n,e));break;case"year":""!==n&&(r=FormEngineValidation.parseYear(n));break;case"null":case"password":break;default:customEvaluations.has(e)?r=customEvaluations.get(e).call(null,n):"object"==typeof TBE_EDITOR&&void 0!==TBE_EDITOR.customEvalFunctions&&"function"==typeof TBE_EDITOR.customEvalFunctions[e]&&(r=TBE_EDITOR.customEvalFunctions[e](n))}return r},FormEngineValidation.validate=function(e){(void 0===e||e instanceof Document)&&formEngineFormElement.querySelectorAll(FormEngineValidation.markerSelector+", .t3js-tabmenu-item").forEach((e=>{e.classList.remove(FormEngineValidation.errorClass,"has-validation-error")}));const n=e||document;for(const e of n.querySelectorAll(FormEngineValidation.rulesSelector))if(null===e.closest(".t3js-flex-section-deleted, .t3js-inline-record-deleted, .t3js-file-reference-deleted")){let n=!1;const t=e.value,a=FormEngineValidation.validateField(e,t);if(Array.isArray(a)&&Array.isArray(t)){if(a.length!==t.length)n=!0;else for(let e=0;e<a.length;e++)if(a[e]!==t[e]){n=!0;break}}else a.length&&t!==a&&(n=!0);n&&(e.disabled&&e.dataset.enableOnModification&&(e.disabled=!1),e.value=a)}},FormEngineValidation.markFieldAsChanged=function(e){if(e instanceof $&&(console.warn("Passing a jQuery element to FormEngineValidation.markFieldAsChanged() is deprecated and will be removed in TYPO3 v14."),console.trace(),e=e.get(0)),!(e instanceof HTMLElement))return;const n=e.closest(".t3js-formengine-palette-field");null!==n&&n.classList.add("has-change")},FormEngineValidation.parseInt=function(e){if(!e)return 0;const n=parseInt(""+e,10);return isNaN(n)?0:n},FormEngineValidation.parseDouble=function(e,n=2){let t=""+e;t=t.replace(/[^0-9,.-]/g,"");const a="-"===t.substring(0,1);t=t.replace(/-/g,""),t=t.replace(/,/g,"."),-1===t.indexOf(".")&&(t+=".0");const i=t.split("."),o=i.pop();let r=Number(i.join("")+"."+o);return a&&(r*=-1),t=r.toFixed(n),t},FormEngineValidation.parseDateTime=function(e){const n=e.indexOf(" ");if(-1!==n){const t=FormEngineValidation.parseDate(e.substring(n+1));FormEngineValidation.lastTime=t+FormEngineValidation.parseTime(e.substring(0,n),"time")}else FormEngineValidation.lastTime=FormEngineValidation.parseDate(e);return FormEngineValidation.lastTime},FormEngineValidation.parseDate=function(e){return FormEngineValidation.lastDate=DateTime.fromFormat(e,"dd-MM-yyyy",{zone:"utc"}).toUnixInteger(),FormEngineValidation.lastDate},FormEngineValidation.parseTime=function(e,n){const t="timesec"===n?"HH:mm:ss":"HH:mm";return FormEngineValidation.lastTime=DateTime.fromFormat(e,t,{zone:"utc"}).set({year:1970,month:1,day:1}).toUnixInteger(),FormEngineValidation.lastTime<0&&(FormEngineValidation.lastTime+=86400),FormEngineValidation.lastTime},FormEngineValidation.parseYear=function(e){let n=parseInt(e,10);return isNaN(n)&&(n=FormEngineValidation.getYear(new Date)),FormEngineValidation.lastYear=n,FormEngineValidation.lastYear},FormEngineValidation.getYear=function(e){return null===e?null:e.getUTCFullYear()},FormEngineValidation.getDate=function(e){const n=new Date(FormEngineValidation.getYear(e),e.getUTCMonth(),e.getUTCDate());return FormEngineValidation.getTimestamp(n)},FormEngineValidation.pol=function(foreign,value){return eval(("-"==foreign?"-":"")+value)},FormEngineValidation.getTimestamp=function(e){return Date.parse(e instanceof Date?e.toISOString():e)/1e3},FormEngineValidation.getTime=function(e){return 60*e.getUTCHours()*60+60*e.getUTCMinutes()+FormEngineValidation.getSecs(e)},FormEngineValidation.getSecs=function(e){return e.getUTCSeconds()},FormEngineValidation.getTimeSecs=function(e){return 60*e.getHours()*60+60*e.getMinutes()+e.getSeconds()},FormEngineValidation.markParentTab=function(e,n){DomHelper.parents(e,".tab-pane").forEach((e=>{n&&(n=null===e.querySelector(".has-error"));const t=e.id;formEngineFormElement.querySelector('a[href="#'+t+'"]').closest(".t3js-tabmenu-item").classList.toggle("has-validation-error",!n)}))},FormEngineValidation.registerSubmitCallback=function(){DocumentSaveActions.getInstance().addPreSubmitCallback((()=>{if(null===document.querySelector("."+FormEngineValidation.errorClass))return!0;const e=Modal.confirm(TYPO3.lang.alert||"Alert",TYPO3.lang["FormEngine.fieldsMissing"],Severity.error,[{text:TYPO3.lang["button.ok"]||"OK",active:!0,btnClass:"btn-default",name:"ok"}]);return e.addEventListener("button.clicked",(()=>e.hideModal())),!1}))},FormEngineValidation}());
\ No newline at end of file
+import $ from"jquery";import{DateTime}from"luxon";import Md5 from"@typo3/backend/hashing/md5.js";import DocumentSaveActions from"@typo3/backend/document-save-actions.js";import Modal from"@typo3/backend/modal.js";import Severity from"@typo3/backend/severity.js";import Utility from"@typo3/backend/utility.js";import RegularEvent from"@typo3/core/event/regular-event.js";import DomHelper from"@typo3/backend/utility/dom-helper.js";import{selector}from"@typo3/core/literals.js";export default(function(){const FormEngineValidation={rulesSelector:"[data-formengine-validation-rules]",inputSelector:"[data-formengine-input-params]",markerSelector:".t3js-formengine-validation-marker",groupFieldHiddenElement:".t3js-formengine-field-group input[type=hidden]",relatedFieldSelector:"[data-relatedfieldname]",errorClass:"has-error",lastYear:0,lastDate:0,lastTime:0,passwordDummy:"********"};let formEngineFormElement;const customEvaluations=new Map;return FormEngineValidation.initialize=function(e){formEngineFormElement=e,formEngineFormElement.querySelectorAll("."+FormEngineValidation.errorClass).forEach((e=>e.classList.remove(FormEngineValidation.errorClass))),FormEngineValidation.initializeInputFields(),new RegularEvent("change",((e,n)=>{FormEngineValidation.validateField(n),FormEngineValidation.markFieldAsChanged(n)})).delegateTo(formEngineFormElement,FormEngineValidation.rulesSelector),FormEngineValidation.registerSubmitCallback();const n=new Date;FormEngineValidation.lastYear=FormEngineValidation.getYear(n),FormEngineValidation.lastDate=FormEngineValidation.getDate(n),FormEngineValidation.lastTime=0,FormEngineValidation.validate()},FormEngineValidation.initializeInputFields=function(){formEngineFormElement.querySelectorAll(FormEngineValidation.inputSelector).forEach((e=>{const n=JSON.parse(e.dataset.formengineInputParams).field,t=formEngineFormElement.querySelector(selector`[name="${n}"]`);"formengineInputInitialized"in e.dataset||(t.dataset.config=e.dataset.formengineInputParams,FormEngineValidation.initializeInputField(n))}))},FormEngineValidation.initializeInputField=function(e){const n=formEngineFormElement.querySelector(selector`[name="${e}"]`),t=formEngineFormElement.querySelector(selector`[data-formengine-input-name="${e}"]`);if(void 0!==n.dataset.config){const e=JSON.parse(n.dataset.config),a=Utility.trimExplode(",",e.evalList);let i=n.value;for(let n=0;n<a.length;n++)i=FormEngineValidation.formatValue(a[n],i,e);i.length&&(t.value=i)}new RegularEvent("change",(()=>{FormEngineValidation.updateInputField(t.dataset.formengineInputName)})).bindTo(t),t.dataset.formengineInputInitialized="true"},FormEngineValidation.registerCustomEvaluation=function(e,n){customEvaluations.has(e)||customEvaluations.set(e,n)},FormEngineValidation.formatValue=function(e,n,t){let a,i,o="";switch(e){case"date":if(n.toString().indexOf("-")>0){o=DateTime.fromISO(n.toString(),{zone:"utc"}).toFormat("dd-MM-yyyy")}else{if(""===n||"0"===n)return"";if(a=parseInt(n.toString(),10),isNaN(a))return"";i=new Date(1e3*a);o=i.getUTCDate().toString(10).padStart(2,"0")+"-"+(i.getUTCMonth()+1).toString(10).padStart(2,"0")+"-"+this.getYear(i)}break;case"datetime":if(""===n||"0"===n)return"";o=(FormEngineValidation.formatValue("time",n,t)+" "+FormEngineValidation.formatValue("date",n,t)).trim();break;case"time":case"timesec":let r;if(n.toString().indexOf("-")>0)r=DateTime.fromISO(n.toString(),{zone:"utc"});else{if(""===n||"0"===n)return"";if(a="number"==typeof n?n:parseInt(n),isNaN(a))return"";r=DateTime.fromSeconds(a,{zone:"utc"})}o="timesec"===e?r.toFormat("HH:mm:ss"):r.toFormat("HH:mm");break;case"password":o=n?FormEngineValidation.passwordDummy:"";break;default:o=n.toString()}return o},FormEngineValidation.updateInputField=function(e){const n=formEngineFormElement.querySelector(selector`[name="${e}"]`),t=formEngineFormElement.querySelector(selector`[data-formengine-input-name="${e}"]`);if(void 0!==n.dataset.config){const e=JSON.parse(n.dataset.config),a=Utility.trimExplode(",",e.evalList);let i=t.value;for(let n=0;n<a.length;n++)i=FormEngineValidation.processValue(a[n],i,e);let o=i;for(let n=0;n<a.length;n++)o=FormEngineValidation.formatValue(a[n],o,e);n.value!==i&&(n.disabled&&n.dataset.enableOnModification&&(n.disabled=!1),n.value=i,n.dispatchEvent(new Event("change")),t.value=o)}},FormEngineValidation.validateField=function(e,n){if(e instanceof $&&(console.warn("Passing a jQuery element to FormEngineValidation.validateField() is deprecated and will be removed in TYPO3 v14."),console.trace(),e=e.get(0)),!(e instanceof HTMLElement))return n;if(n=n||e.value||"",void 0===e.dataset.formengineValidationRules)return n;const t=JSON.parse(e.dataset.formengineValidationRules);let a=!1,i=0;const o=n;let r,l,s;Array.isArray(n)||(n=n.trimStart());for(const o of t){if(a)break;switch(o.type){case"required":""===n&&(a=!0,e.closest(FormEngineValidation.markerSelector).classList.add(FormEngineValidation.errorClass));break;case"range":if(""!==n){if((o.minItems||o.maxItems)&&(r=formEngineFormElement.querySelector(selector`[name="${e.dataset.relatedfieldname}"]`),i=null!==r?Utility.trimExplode(",",r.value).length:parseInt(e.value,10),void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0))),void 0!==o.lower){const e=1*o.lower;!isNaN(e)&&parseInt(n,10)<e&&(a=!0)}if(void 0!==o.upper){const e=1*o.upper;!isNaN(e)&&parseInt(n,10)>e&&(a=!0)}}break;case"select":case"category":(o.minItems||o.maxItems)&&(r=formEngineFormElement.querySelector(selector`[name="${e.dataset.relatedfieldname}"]`),i=null!==r?Utility.trimExplode(",",r.value).length:e instanceof HTMLSelectElement?e.querySelectorAll("option:checked").length:e.querySelectorAll("input[value]:checked").length,void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0)));break;case"group":case"folder":case"inline":(o.minItems||o.maxItems)&&(i=Utility.trimExplode(",",e.value).length,void 0!==o.minItems&&(l=1*o.minItems,!isNaN(l)&&i<l&&(a=!0)),void 0!==o.maxItems&&(s=1*o.maxItems,!isNaN(s)&&i>s&&(a=!0)));break;case"min":(e instanceof HTMLInputElement||e instanceof HTMLTextAreaElement)&&e.value.length>0&&e.value.length<e.minLength&&(a=!0)}}const m=!a,d=e.closest(FormEngineValidation.markerSelector);return null!==d&&d.classList.toggle(FormEngineValidation.errorClass,!m),FormEngineValidation.markParentTab(e,m),formEngineFormElement.dispatchEvent(new CustomEvent("t3-formengine-postfieldvalidation",{cancelable:!1,bubbles:!0})),o},FormEngineValidation.processValue=function(e,n,t){let a="",i="",o=0,r=n;switch(e){case"alpha":case"num":case"alphanum":case"alphanum_x":for(a="",o=0;o<n.length;o++){const t=n.substr(o,1);let i="_"===t||"-"===t,r=t>="a"&&t<="z"||t>="A"&&t<="Z",l=t>="0"&&t<="9";switch(e){case"alphanum":i=!1;break;case"alpha":l=!1,i=!1;break;case"num":r=!1,i=!1}(r||l||i)&&(a+=t)}a!==n&&(r=a);break;case"is_in":if(t.is_in){i=""+n,t.is_in=t.is_in.replace(/[-[\]{}()*+?.,\\^$|#\s]/g,"\\$&");const e=new RegExp("[^"+t.is_in+"]+","g");a=i.replace(e,"")}else a=i;r=a;break;case"nospace":r=(""+n).replace(/ /g,"");break;case"md5":""!==n&&(r=Md5.hash(n));break;case"upper":r=n.toUpperCase();break;case"lower":r=n.toLowerCase();break;case"integer":""!==n&&(r=FormEngineValidation.parseInt(n));break;case"decimal":""!==n&&(r=FormEngineValidation.parseDouble(n));break;case"trim":r=String(n).trim();break;case"datetime":""!==n&&(r=FormEngineValidation.parseDateTime(n));break;case"date":""!==n&&(r=FormEngineValidation.parseDate(n));break;case"time":case"timesec":""!==n&&(r=FormEngineValidation.parseTime(n,e));break;case"year":""!==n&&(r=FormEngineValidation.parseYear(n));break;case"null":case"password":break;default:customEvaluations.has(e)?r=customEvaluations.get(e).call(null,n):"object"==typeof TBE_EDITOR&&void 0!==TBE_EDITOR.customEvalFunctions&&"function"==typeof TBE_EDITOR.customEvalFunctions[e]&&(r=TBE_EDITOR.customEvalFunctions[e](n))}return r},FormEngineValidation.validate=function(e){(void 0===e||e instanceof Document)&&formEngineFormElement.querySelectorAll(FormEngineValidation.markerSelector+", .t3js-tabmenu-item").forEach((e=>{e.classList.remove(FormEngineValidation.errorClass,"has-validation-error")}));const n=e||document;for(const e of n.querySelectorAll(FormEngineValidation.rulesSelector))if(null===e.closest(".t3js-flex-section-deleted, .t3js-inline-record-deleted, .t3js-file-reference-deleted")){let n=!1;const t=e.value,a=FormEngineValidation.validateField(e,t);if(Array.isArray(a)&&Array.isArray(t)){if(a.length!==t.length)n=!0;else for(let e=0;e<a.length;e++)if(a[e]!==t[e]){n=!0;break}}else a.length&&t!==a&&(n=!0);n&&(e.disabled&&e.dataset.enableOnModification&&(e.disabled=!1),e.value=a)}},FormEngineValidation.markFieldAsChanged=function(e){if(e instanceof $&&(console.warn("Passing a jQuery element to FormEngineValidation.markFieldAsChanged() is deprecated and will be removed in TYPO3 v14."),console.trace(),e=e.get(0)),!(e instanceof HTMLElement))return;const n=e.closest(".t3js-formengine-palette-field");null!==n&&n.classList.add("has-change")},FormEngineValidation.parseInt=function(e){if(!e)return 0;const n=parseInt(""+e,10);return isNaN(n)?0:n},FormEngineValidation.parseDouble=function(e,n=2){let t=""+e;t=t.replace(/[^0-9,.-]/g,"");const a=t.startsWith("-");t=t.replace(/-/g,""),t=t.replace(/,/g,"."),-1===t.indexOf(".")&&(t+=".0");const i=t.split("."),o=i.pop();let r=Number(i.join("")+"."+o);return a&&(r*=-1),t=r.toFixed(n),t},FormEngineValidation.parseDateTime=function(e){const n=e.indexOf(" ");if(-1!==n){const t=FormEngineValidation.parseDate(e.substring(n+1));FormEngineValidation.lastTime=t+FormEngineValidation.parseTime(e.substring(0,n),"time")}else FormEngineValidation.lastTime=FormEngineValidation.parseDate(e);return FormEngineValidation.lastTime},FormEngineValidation.parseDate=function(e){return FormEngineValidation.lastDate=DateTime.fromFormat(e,"dd-MM-yyyy",{zone:"utc"}).toUnixInteger(),FormEngineValidation.lastDate},FormEngineValidation.parseTime=function(e,n){const t="timesec"===n?"HH:mm:ss":"HH:mm";return FormEngineValidation.lastTime=DateTime.fromFormat(e,t,{zone:"utc"}).set({year:1970,month:1,day:1}).toUnixInteger(),FormEngineValidation.lastTime<0&&(FormEngineValidation.lastTime+=86400),FormEngineValidation.lastTime},FormEngineValidation.parseYear=function(e){let n=parseInt(e,10);return isNaN(n)&&(n=FormEngineValidation.getYear(new Date)),FormEngineValidation.lastYear=n,FormEngineValidation.lastYear},FormEngineValidation.getYear=function(e){return null===e?null:e.getUTCFullYear()},FormEngineValidation.getDate=function(e){const n=new Date(FormEngineValidation.getYear(e),e.getUTCMonth(),e.getUTCDate());return FormEngineValidation.getTimestamp(n)},FormEngineValidation.pol=function(foreign,value){return eval(("-"==foreign?"-":"")+value)},FormEngineValidation.getTimestamp=function(e){return Date.parse(e instanceof Date?e.toISOString():e)/1e3},FormEngineValidation.getTime=function(e){return 60*e.getUTCHours()*60+60*e.getUTCMinutes()+FormEngineValidation.getSecs(e)},FormEngineValidation.getSecs=function(e){return e.getUTCSeconds()},FormEngineValidation.getTimeSecs=function(e){return 60*e.getHours()*60+60*e.getMinutes()+e.getSeconds()},FormEngineValidation.markParentTab=function(e,n){DomHelper.parents(e,".tab-pane").forEach((e=>{n&&(n=null===e.querySelector(".has-error"));const t=e.id;formEngineFormElement.querySelector('a[href="#'+t+'"]').closest(".t3js-tabmenu-item").classList.toggle("has-validation-error",!n)}))},FormEngineValidation.registerSubmitCallback=function(){DocumentSaveActions.getInstance().addPreSubmitCallback((()=>{if(null===document.querySelector("."+FormEngineValidation.errorClass))return!0;const e=Modal.confirm(TYPO3.lang.alert||"Alert",TYPO3.lang["FormEngine.fieldsMissing"],Severity.error,[{text:TYPO3.lang["button.ok"]||"OK",active:!0,btnClass:"btn-default",name:"ok"}]);return e.addEventListener("button.clicked",(()=>e.hideModal())),!1}))},FormEngineValidation}());
\ No newline at end of file
diff --git a/typo3/sysext/rte_ckeditor/Resources/Public/JavaScript/rte-link-browser.js b/typo3/sysext/rte_ckeditor/Resources/Public/JavaScript/rte-link-browser.js
index 6ad448bdf7c6b7f4032b74d6c6fc72ebc39ca1c0..b49fdfa4b1bc3142383ce846a700eba7043c9c4d 100644
--- a/typo3/sysext/rte_ckeditor/Resources/Public/JavaScript/rte-link-browser.js
+++ b/typo3/sysext/rte_ckeditor/Resources/Public/JavaScript/rte-link-browser.js
@@ -10,4 +10,4 @@
  *
  * The TYPO3 project - inspiring people to share!
  */
-import LinkBrowser from"@typo3/backend/link-browser.js";import Modal from"@typo3/backend/modal.js";import RegularEvent from"@typo3/core/event/regular-event.js";import{LINK_ALLOWED_ATTRIBUTES,addLinkPrefix}from"@typo3/rte-ckeditor/plugin/typo3-link.js";class RteLinkBrowser{constructor(){this.editor=null,this.selectionStartPosition=null,this.selectionEndPosition=null}initialize(){this.editor=Modal.currentModal.userData.editor,this.selectionStartPosition=Modal.currentModal.userData.selectionStartPosition,this.selectionEndPosition=Modal.currentModal.userData.selectionEndPosition;const t=document.querySelector(".t3js-removeCurrentLink");null!==t&&new RegularEvent("click",(t=>{t.preventDefault(),this.restoreSelection(),this.editor.execute("unlink"),Modal.dismiss()})).bindTo(t)}finalizeFunction(t){const e=LinkBrowser.getLinkAttributeValues(),i=e.params?e.params:"";delete e.params;const n=this.convertAttributes(e,"");this.restoreSelection(),this.editor.execute("link",this.sanitizeLink(t,i),n),Modal.dismiss()}restoreSelection(){this.editor.model.change((t=>{const e=[t.createRange(this.selectionStartPosition,this.selectionEndPosition)];t.setSelection(e)}))}convertAttributes(t,e){const i={attrs:{}};for(const[e,n]of Object.entries(t))LINK_ALLOWED_ATTRIBUTES.includes(e)&&(i.attrs[addLinkPrefix(e)]=n);return"string"==typeof e&&""!==e&&(i.linkText=e),i}sanitizeLink(t,e){const i=t.match(/^([a-z0-9]+:\/\/[^:/?#]+(?:\/?[^?#]*)?)(\??[^#]*)(#?.*)$/);if(i&&i.length>0){t=i[1]+i[2];const n=i[2].length>0?"&":"?";e.length>0&&("&"===e[0]&&(e=e.substr(1)),e.length>0&&(t+=n+e)),t+=i[3]}return t}}const rteLinkBrowser=new RteLinkBrowser;export default rteLinkBrowser;LinkBrowser.finalizeFunction=t=>{rteLinkBrowser.finalizeFunction(t)};
\ No newline at end of file
+import LinkBrowser from"@typo3/backend/link-browser.js";import Modal from"@typo3/backend/modal.js";import RegularEvent from"@typo3/core/event/regular-event.js";import{LINK_ALLOWED_ATTRIBUTES,addLinkPrefix}from"@typo3/rte-ckeditor/plugin/typo3-link.js";class RteLinkBrowser{constructor(){this.editor=null,this.selectionStartPosition=null,this.selectionEndPosition=null}initialize(){this.editor=Modal.currentModal.userData.editor,this.selectionStartPosition=Modal.currentModal.userData.selectionStartPosition,this.selectionEndPosition=Modal.currentModal.userData.selectionEndPosition;const t=document.querySelector(".t3js-removeCurrentLink");null!==t&&new RegularEvent("click",(t=>{t.preventDefault(),this.restoreSelection(),this.editor.execute("unlink"),Modal.dismiss()})).bindTo(t)}finalizeFunction(t){const e=LinkBrowser.getLinkAttributeValues(),i=e.params?e.params:"";delete e.params;const n=this.convertAttributes(e,"");this.restoreSelection(),this.editor.execute("link",this.sanitizeLink(t,i),n),Modal.dismiss()}restoreSelection(){this.editor.model.change((t=>{const e=[t.createRange(this.selectionStartPosition,this.selectionEndPosition)];t.setSelection(e)}))}convertAttributes(t,e){const i={attrs:{}};for(const[e,n]of Object.entries(t))LINK_ALLOWED_ATTRIBUTES.includes(e)&&(i.attrs[addLinkPrefix(e)]=n);return"string"==typeof e&&""!==e&&(i.linkText=e),i}sanitizeLink(t,e){const i=t.match(/^([a-z0-9]+:\/\/[^:/?#]+(?:\/?[^?#]*)?)(\??[^#]*)(#?.*)$/);if(i&&i.length>0){t=i[1]+i[2];const n=i[2].length>0?"&":"?";e.length>0&&(e.startsWith("&")&&(e=e.substr(1)),e.length>0&&(t+=n+e)),t+=i[3]}return t}}const rteLinkBrowser=new RteLinkBrowser;export default rteLinkBrowser;LinkBrowser.finalizeFunction=t=>{rteLinkBrowser.finalizeFunction(t)};
\ No newline at end of file