· 4 years ago · Apr 02, 2021, 12:58 PM
1/**
2 * Pimcore
3 *
4 * This source file is available under two different licenses:
5 * - GNU General Public License version 3 (GPLv3)
6 * - Pimcore Enterprise License (PEL)
7 * Full copyright and license information is available in
8 * LICENSE.md which is distributed with this source code.
9 *
10 * @copyright  Copyright (c) Pimcore GmbH (http://www.pimcore.org)
11 * @license    http://www.pimcore.org/license     GPLv3 and PEL
12 */
13
14
15// debug
16if (typeof console == "undefined") {
17    console = {
18        log: function (v) {
19        },
20        dir: function (v) {
21        },
22        debug: function (v) {
23        },
24        info: function (v) {
25        },
26        warn: function (v) {
27        },
28        error: function (v) {
29        },
30        trace: function (v) {
31        },
32        group: function (v) {
33        },
34        groupEnd: function (v) {
35        },
36        time: function (v) {
37        },
38        timeEnd: function (v) {
39        },
40        profile: function (v) {
41        },
42        profileEnd: function (v) {
43        }
44    };
45}
46
47var xhrActive = 0; // number of active xhr requests
48
49Ext.Loader.setConfig({
50    enabled: true
51});
52Ext.enableAriaButtons = false;
53
54Ext.Loader.setPath('Ext.ux', '/bundles/pimcoreadmin/js/lib/ext/ux');
55
56Ext.require([
57    'Ext.button.Split',
58    'Ext.container.Viewport',
59    'Ext.data.JsonStore',
60    'Ext.grid.column.Action',
61    'Ext.grid.plugin.CellEditing',
62    'Ext.form.field.ComboBox',
63    'Ext.form.field.Hidden',
64    'Ext.grid.column.Check',
65    'Ext.grid.property.Grid',
66    'Ext.form.field.Time',
67    'Ext.form.FieldSet',
68    'Ext.form.Label',
69    'Ext.form.Panel',
70    'Ext.grid.feature.Grouping',
71    'Ext.grid.Panel',
72    'Ext.grid.plugin.DragDrop',
73    'Ext.layout.container.Accordion',
74    'Ext.layout.container.Border',
75    'Ext.tip.QuickTipManager',
76    'Ext.tab.Panel',
77    'Ext.toolbar.Paging',
78    'Ext.toolbar.Spacer',
79    'Ext.tree.plugin.TreeViewDragDrop',
80    'Ext.tree.Panel',
81    'Ext.ux.colorpick.Field',
82    'Ext.ux.colorpick.SliderAlpha',
83    'Ext.ux.DataTip',
84    'Ext.ux.form.MultiSelect',
85    'Ext.ux.TabCloseMenu',
86    'Ext.ux.TabReorderer',
87    'Ext.ux.grid.SubTable',
88    'Ext.window.Toast'
89]);
90
91
92Ext.onReady(function () {
93
94    pimcore.helpers.colorpicker.initOverrides();
95
96    var StateFullProvider = Ext.extend(Ext.state.Provider, {
97        namespace: "default",
98
99        constructor: function (config) {
100            StateFullProvider.superclass.constructor.call(this);
101            Ext.apply(this, config);
102
103            var data = localStorage.getItem(this.namespace);
104            if (!data) {
105                this.state = {};
106            } else {
107                data = JSON.parse(data);
108                if (data.state && data.user == pimcore.currentuser.id) {
109                    this.state = data.state;
110                } else {
111                    this.state = {};
112                }
113            }
114        },
115
116        get: function (name, defaultValue) {
117            try {
118                if (typeof this.state[name] == "undefined") {
119                    return defaultValue
120                } else {
121                    return this.decodeValue(this.state[name])
122                }
123            } catch (e) {
124                this.clear(name);
125                return defaultValue;
126            }
127        },
128        set: function (name, value) {
129            try {
130                if (typeof value == "undefined" || value === null) {
131                    this.clear(name);
132                    return;
133                }
134                this.state[name] = this.encodeValue(value)
135
136                var data = {
137                    state: this.state,
138                    user: pimcore.currentuser.id
139                };
140                var json = JSON.stringify(data);
141
142                localStorage.setItem(this.namespace, json);
143            } catch (e) {
144                this.clear(name);
145            }
146
147            this.fireEvent("statechange", this, name, value);
148        }
149    });
150
151
152    var provider = new StateFullProvider({
153        namespace: "pimcore_ui_states_6"
154    });
155
156    Ext.state.Manager.setProvider(provider);
157
158    // confirmation to close pimcore
159    window.onbeforeunload = function () {
160
161        // set this here as a global so that eg. the editmode can access this (edit::iframeOnbeforeunload()),
162        // to prevent multiple warning messages to be shown
163        pimcore.globalmanager.add("pimcore_reload_in_progress", true);
164
165        if (!pimcore.settings.devmode) {
166            // check for opened tabs and if the user has configured the warnings
167            var tabPanel = Ext.getCmp("pimcore_panel_tabs");
168            var user = pimcore.globalmanager.get("user");
169            if (pimcore.settings.showCloseConfirmation && tabPanel.items.getCount() > 0 && user["closeWarning"]) {
170                return t("do_you_really_want_to_close_pimcore");
171            }
172        }
173    };
174
175    Ext.QuickTips.init();
176    Ext.MessageBox.minPromptWidth = 500;
177
178    Ext.Ajax.setDisableCaching(true);
179    Ext.Ajax.setTimeout(900000);
180    Ext.Ajax.setMethod("GET");
181    Ext.Ajax.setDefaultHeaders({
182        'X-pimcore-csrf-token': pimcore.settings["csrfToken"],
183        'X-pimcore-extjs-version-major': Ext.getVersion().getMajor(),
184        'X-pimcore-extjs-version-minor': Ext.getVersion().getMinor()
185    });
186    Ext.Ajax.on('requestexception', function (conn, response, options) {
187        console.log("xhr request failed");
188
189        var jsonData = null;
190        try {
191            jsonData = Ext.decode(response.responseText);
192        } catch (e) {
193
194        }
195
196        var date = new Date();
197        var errorMessage = "Timestamp: " + date.toString() + "\n";
198        var errorDetailMessage = "\n" + response.responseText;
199
200        try {
201            errorMessage += "Status: " + response.status + " | " + response.statusText + "\n";
202            errorMessage += "URL: " + options.url + "\n";
203
204            if (options["params"] && options["params"].length > 0) {
205                errorMessage += "Params:\n";
206                Ext.iterate(options.params, function (key, value) {
207                    errorMessage += ("-> " + key + ": " + value.substr(0, 500) + "\n");
208                });
209            }
210
211            if (options["method"]) {
212                errorMessage += "Method: " + options.method + "\n";
213            }
214
215            if(jsonData) {
216                if (jsonData['message']) {
217                    errorDetailMessage = jsonData['message'];
218                }
219
220                if(jsonData['traceString']) {
221                    errorDetailMessage += "\nTrace: \n" + jsonData['traceString'];
222                }
223            }
224
225            errorMessage += "Message: " + errorDetailMessage;
226        } catch (e) {
227            errorMessage += "\n\n";
228            errorMessage += response.responseText;
229        }
230
231        if (!response.aborted && options["ignoreErrors"] !== true) {
232            if (response.status === 503) {
233                //show wait info
234                if (!pimcore.maintenanceWindow) {
235                    pimcore.maintenanceWindow = new Ext.Window({
236                        closable: false,
237                        title: t("please_wait"),
238                        bodyStyle: "padding: 20px;",
239                        html: t("the_system_is_in_maintenance_mode_please_wait"),
240                        closeAction: "close",
241                        modal: true
242                    });
243                    pimcore.viewport.add(pimcore.maintenanceWindow);
244                    pimcore.maintenanceWindow.show();
245                }
246            } else if (response.status === 403) {
247                if(jsonData && jsonData['type'] === 'ValidationException') {
248                    pimcore.helpers.showNotification(t("validation_failed"), jsonData['message'], "error", errorMessage);
249                } else {
250                    pimcore.helpers.showNotification(t("access_denied"), t("access_denied_description"), "error");
251                }
252            } else {
253                var message = t("error_general");
254                if(jsonData && jsonData['message']) {
255                    message = jsonData['message'] + "<br><br>" + t("error_general");
256                }
257
258                pimcore.helpers.showNotification(t("error"), message, "error", errorMessage);
259            }
260        }
261
262        xhrActive--;
263        if (xhrActive < 1) {
264            Ext.get("pimcore_loading").hide();
265        }
266
267    });
268    Ext.Ajax.on("beforerequest", function () {
269        if (xhrActive < 1) {
270            Ext.get("pimcore_loading").show();
271        }
272        xhrActive++;
273    });
274    Ext.Ajax.on("requestcomplete", function (conn, response, options) {
275        xhrActive--;
276        if (xhrActive < 1) {
277            Ext.get("pimcore_loading").hide();
278        }
279    });
280
281    var user = new pimcore.user(pimcore.currentuser);
282    pimcore.globalmanager.add("user", user);
283
284    var docTypesUrl = '/admin/document/doc-types?';
285    // document types
286    Ext.define('pimcore.model.doctypes', {
287        extend: 'Ext.data.Model',
288        fields: [
289            'id',
290            {name: 'name', allowBlank: false},
291            {
292                name: "translatedName",
293                convert: function (v, rec) {
294                    return ts(rec.data.name);
295                },
296                depends : ['name']
297            },
298            'module',
299            'controller',
300            'action',
301            'template',
302            {name: 'type', allowBlank: false},
303            'priority',
304            'creationDate',
305            'modificationDate'
306        ],
307        proxy: {
308            type: 'ajax',
309            reader: {
310                type: 'json',
311                totalProperty: 'total',
312                successProperty: 'success',
313                rootProperty: 'data'
314            },
315            writer: {
316                type: 'json',
317                writeAllFields: true,
318                rootProperty: 'data',
319                encode: 'true'
320            },
321            api: {
322                create: docTypesUrl + "xaction=create",
323                read: docTypesUrl + "xaction=read",
324                update: docTypesUrl + "xaction=update",
325                destroy: docTypesUrl + "xaction=destroy"
326            }
327        }
328    });
329
330    if (user.isAllowed("documents") || user.isAllowed("users")) {
331        var store = new Ext.data.Store({
332            id: 'doctypes',
333            model: 'pimcore.model.doctypes',
334            remoteSort: false,
335            autoSync: true,
336            autoLoad: true
337        });
338
339        pimcore.globalmanager.add("document_types_store", store);
340    }
341
342    //translation admin keys
343    pimcore.globalmanager.add("translations_admin_missing", new Array());
344    pimcore.globalmanager.add("translations_admin_added", new Array());
345    pimcore.globalmanager.add("translations_admin_translated_values", new Array());
346
347
348    var objectClassFields = [
349        {name: 'id'},
350        {name: 'text', allowBlank: false},
351        {
352            name: "translatedText", convert: function (v, rec) {
353                return ts(rec.data.text);
354            }
355        },
356        {name: 'icon'},
357        {name: 'group'},
358        {name: "propertyVisibility"}
359    ];
360
361    Ext.define('pimcore.model.objecttypes', {
362        extend: 'Ext.data.Model',
363        fields: objectClassFields,
364        proxy: {
365            type: 'ajax',
366            url: '/admin/class/get-tree',
367            reader: {
368                type: 'json'
369            }
370        }
371    });
372
373    var storeo = new Ext.data.Store({
374        model: 'pimcore.model.objecttypes',
375        id: 'object_types'
376    });
377    storeo.load();
378
379    pimcore.globalmanager.add("object_types_store", storeo);
380
381
382    // a store for filtered classes that can be created by the user
383    Ext.define('pimcore.model.objecttypes.create', {
384        extend: 'Ext.data.Model',
385        fields: objectClassFields,
386        proxy: {
387            type: 'ajax',
388            url: '/admin/class/get-tree?createAllowed=true',
389            reader: {
390                type: 'json'
391            }
392        }
393    });
394
395    var storeoc = new Ext.data.Store({
396        model: 'pimcore.model.objecttypes.create',
397        id: 'object_types'
398    });
399    storeoc.load();
400
401    pimcore.globalmanager.add("object_types_store_create", storeoc);
402
403    pimcore.globalmanager.add("perspective", new pimcore.perspective(pimcore.settings.perspective));
404
405
406    //pimcore languages
407    Ext.define('pimcore.model.languages', {
408        extend: 'Ext.data.Model',
409        fields: [
410            {name: 'language'},
411            {name: 'display'}
412        ],
413        proxy: {
414            type: 'ajax',
415            url: '/admin/settings/get-available-admin-languages',
416            reader: {
417                type: 'json'
418            }
419        }
420    });
421
422
423    var languageStore = new Ext.data.Store({
424        model: "pimcore.model.languages"
425    });
426    languageStore.load();
427    pimcore.globalmanager.add("pimcorelanguages", languageStore);
428
429    Ext.define('pimcore.model.sites', {
430        extend: 'Ext.data.Model',
431        fields: ["id", "domains", "rootId", "rootPath", "domain"],
432        proxy: {
433            type: 'ajax',
434            url: '/admin/settings/get-available-sites',
435            reader: {
436                type: 'json'
437            }
438        }
439    });
440
441    var sitesStore = new Ext.data.Store({
442        model: "pimcore.model.sites"
443        //restful:false,
444        //proxy:sitesProxy,
445        //reader:sitesReader
446    });
447    sitesStore.load();
448    pimcore.globalmanager.add("sites", sitesStore);
449
450    // target groups
451    Ext.define('pimcore.model.target_groups', {
452        extend: 'Ext.data.Model',
453        fields: ["id", "text"]
454    });
455
456    var targetGroupStore = Ext.create('Ext.data.JsonStore', {
457        model: "pimcore.model.target_groups",
458        proxy: {
459            type: 'ajax',
460            url: '/admin/targeting/target-group/list',
461            reader: {
462                type: 'json'
463            }
464        }
465    });
466
467    targetGroupStore.load();
468    pimcore.globalmanager.add("target_group_store", targetGroupStore);
469
470
471    // check for updates
472    window.setTimeout(function () {
473
474        var domains = '';
475        pimcore.globalmanager.get("sites").each(function (rec) {
476            if(rec.get('rootId') !== 1) {
477                if(!empty(rec.get('domain'))) {
478                    domains += rec.get('domain') + ",";
479                }
480                if(!empty(rec.get('domains'))) {
481                    domains += rec.get('domains') + ",";
482                }
483            }
484        });
485
486        // use vanilla javascript instead of ExtJS to bypass default error handling
487        var request = new XMLHttpRequest();
488        request.open('POST', "https://liveupdate.pimcore.org/update-check", false);
489
490        request.onload = function() {
491            if (this.status >= 200 && this.status < 400) {
492                var data = Ext.decode(this.response);
493                if (data.latestVersion) {
494                    if (pimcore.currentuser.admin) {
495
496                        pimcore.notification.helper.incrementCount();
497
498                        var toolbar = pimcore.globalmanager.get("layout_toolbar");
499                        toolbar.notificationMenu.add({
500                            text: t("update_available"),
501                            iconCls: "pimcore_icon_reload",
502                            handler: function () {
503                                var html = '<div class="pimcore_about_window" xmlns="http://www.w3.org/1999/html">';
504                                html += '<h2 style="text-decoration: underline">New Version Available!</h2>';
505                                html += '<br><b>Your Version: ' + pimcore.settings.version + '</b>';
506                                html += '<br><b style="color: darkgreen;">New Version: ' + data.latestVersion + '</b>';
507                                html += '<h3 style="color: darkred">Please update as soon as possible!</h3>';
508                                html += '</div>';
509
510                                var win = new Ext.Window({
511                                    title: "New Version Available!",
512                                    width: 500,
513                                    height: 220,
514                                    bodyStyle: "padding: 10px;",
515                                    modal: true,
516                                    html: html
517                                });
518                                win.show();
519                            }
520                        });
521                    }
522                }
523
524                if (data.pushStatistics) {
525                    var request = new XMLHttpRequest();
526                    request.open('GET', "/admin/index/statistics", false);
527
528                    request.onload = function () {
529                        if (this.status >= 200 && this.status < 400) {
530                            var res = Ext.decode(this.response);
531
532                            var request = new XMLHttpRequest();
533                            request.open('POST', "https://liveupdate.pimcore.org/statistics", false);
534
535                            var data = new FormData();
536                            data.append('data', encodeURIComponent(JSON.stringify(res)));
537
538                            request.send(data);
539                        }
540                    };
541                    request.send(data);
542                }
543            }
544        };
545
546        var data = new FormData();
547        data.append('id', pimcore.settings.instanceId);
548        data.append('revision', pimcore.settings.build);
549        data.append('version', pimcore.settings.version);
550        data.append('debug', pimcore.settings.debug);
551        data.append('devmode', pimcore.settings.devmode);
552        data.append('environment', pimcore.settings.environment);
553        data.append("language", pimcore.settings.language);
554        data.append("main_domain", pimcore.settings.main_domain);
555        data.append("domains", domains);
556        data.append("timezone", pimcore.settings.timezone);
557        data.append("websiteLanguages", pimcore.settings.websiteLanguages.join(','));
558
559        request.send(data);
560
561    }, 5000);
562
563
564    // remove loading
565    Ext.get("pimcore_loading").addCls("loaded");
566    Ext.get("pimcore_loading").hide();
567    Ext.get("pimcore_signet").show();
568
569    // init general layout
570    try {
571        pimcore.viewport = Ext.create('Ext.container.Viewport', {
572            id: "pimcore_viewport",
573            layout: 'fit',
574            items: [
575                {
576                    xtype: "panel",
577                    id: "pimcore_body",
578                    cls: "pimcore_body",
579                    layout: "border",
580                    border: false,
581                    items: [
582                        Ext.create('Ext.panel.Panel',
583                            {
584                                region: 'west',
585                                id: 'pimcore_panel_tree_left',
586                                cls: 'pimcore_main_accordion',
587                                split: {
588                                    cls: 'pimcore_main_splitter'
589                                },
590                                width: 300,
591                                minSize: 175,
592                                collapsible: true,
593                                collapseMode: 'header',
594                                defaults: {
595                                    margin: '0'
596                                },
597                                layout: {
598                                    type: 'accordion',
599                                    hideCollapseTool: true,
600                                    animate: false
601                                },
602                                header: false,
603                                hidden: true,
604                                forceLayout: true,
605                                hideMode: "offsets",
606                                items: []
607                            }
608                        )
609                        ,
610                        Ext.create('Ext.tab.Panel', {
611                            region: 'center',
612                            deferredRender: false,
613                            id: "pimcore_panel_tabs",
614                            enableTabScroll: true,
615                            hideMode: "offsets",
616                            cls: "tab_panel",
617                            plugins:
618                                [
619                                    Ext.create('Ext.ux.TabCloseMenu', {
620                                        pluginId: 'tabclosemenu',
621                                        showCloseAll: false,
622                                        closeTabText: t("close_tab"),
623                                        showCloseOthers: false,
624                                        extraItemsTail: pimcore.helpers.getMainTabMenuItems()
625                                    }),
626                                    Ext.create('Ext.ux.TabReorderer', {}),
627                                    Ext.create('Ext.ux.TabMiddleButtonClose', {})
628                                ]
629                        })
630                        ,
631                        {
632                            region: 'east',
633                            id: 'pimcore_panel_tree_right',
634                            cls: "pimcore_main_accordion",
635                            split: {
636                                cls: 'pimcore_main_splitter'
637                            },
638                            width: 300,
639                            minSize: 175,
640                            collapsible: true,
641                            collapseMode: 'header',
642                            defaults: {
643                                margin: '0'
644                            },
645                            layout: {
646                                type: 'accordion',
647                                hideCollapseTool: true,
648                                animate: false
649                            },
650                            header: false,
651                            hidden: true,
652                            forceLayout: true,
653                            hideMode: "offsets",
654                            items: []
655                        }
656                    ]
657                }
658            ],
659            listeners: {
660                "afterrender": function (el) {
661                    Ext.get("pimcore_navigation").show();
662                    Ext.get("pimcore_avatar").show();
663                    Ext.get("pimcore_logout").show();
664
665                    pimcore.helpers.initMenuTooltips();
666
667                    var loadMask = new Ext.LoadMask(
668                        {
669                            target: Ext.getCmp("pimcore_viewport"),
670                            msg: t("please_wait")
671                        });
672                    loadMask.enable();
673                    pimcore.globalmanager.add("loadingmask", loadMask);
674
675
676                    // prevent dropping files / folder outside the asset tree
677                    var fn = function (e) {
678                        e.preventDefault();
679                        e.dataTransfer.dropEffect = 'none';
680                    };
681
682                    el.getEl().dom.addEventListener("dragenter", fn, true);
683                    el.getEl().dom.addEventListener("dragover", fn, true);
684
685                    // open "My Profile" when clicking on avatar
686                    Ext.get("pimcore_avatar").on("click", function (ev) {
687                        pimcore.helpers.openProfile();
688                    });
689                }
690            }
691        });
692
693        // add sidebar panels
694
695        if (user.memorizeTabs || pimcore.helpers.forceOpenMemorizedTabsOnce()) {
696            // open previous opened tabs after the trees are ready
697            pimcore.layout.treepanelmanager.addOnReadyCallback(function () {
698                window.setTimeout(function () {
699                    pimcore.helpers.openMemorizedTabs();
700                }, 500);
701            });
702        }
703
704
705        var perspective = pimcore.globalmanager.get("perspective");
706        var elementTree = perspective.getElementTree();
707
708        var locateConfigs = {
709            document: [],
710            asset: [],
711            object: []
712        };
713
714        for (var i = 0; i < elementTree.length; i++) {
715
716            var treeConfig = elementTree[i];
717            var type = treeConfig["type"];
718            var side = treeConfig["position"] ? treeConfig["position"] : "left";
719            var expanded = treeConfig["expanded"];
720            var treepanel = null;
721            var tree = null;
722            var treetype = null;
723
724            var locateKey = "layout_" + type + "_locateintree_tree";
725
726            switch (type) {
727                case "documents":
728                    if (user.isAllowed("documents") && !treeConfig.hidden) {
729                        treetype = "document";
730                        tree = new pimcore.document.tree(null, treeConfig);
731                        pimcore.globalmanager.add("layout_document_tree", tree);
732                        treepanel = Ext.getCmp("pimcore_panel_tree_" + side);
733                        treepanel.setHidden(false);
734                    }
735                    break;
736                case "assets":
737                    if (user.isAllowed("assets") && !treeConfig.hidden) {
738                        treetype = "asset";
739                        tree = new pimcore.asset.tree(null, treeConfig);
740                        pimcore.globalmanager.add("layout_asset_tree", tree);
741                        treepanel = Ext.getCmp("pimcore_panel_tree_" + side);
742                        treepanel.setHidden(false);
743                    }
744                    break;
745                case "objects":
746                    if (user.isAllowed("objects")) {
747                        treetype = "object";
748                        if (!treeConfig.hidden) {
749                            treepanel = Ext.getCmp("pimcore_panel_tree_" + side);
750                            tree = new pimcore.object.tree(null, treeConfig);
751                            pimcore.globalmanager.add("layout_object_tree", tree);
752                            treepanel.setHidden(false);
753                        }
754                    }
755                    break;
756                case "customview":
757                    if (!treeConfig.hidden) {
758                        treetype = treeConfig.treetype ? treeConfig.treetype : "object";
759                        locateKey = "layout_" + treetype + "s_locateintree_tree";
760
761                        if (user.isAllowed(treetype + "s")) {
762                            treepanel = Ext.getCmp("pimcore_panel_tree_" + side);
763
764                            var treeCls = window.pimcore[treetype].customviews.tree;
765
766                            tree = new treeCls({
767                                isCustomView: true,
768                                customViewId: treeConfig.id,
769                                allowedClasses: treeConfig.allowedClasses,
770                                rootId: treeConfig.rootId,
771                                rootVisible: treeConfig.showroot,
772                                treeId: "pimcore_panel_tree_" + treetype + "_" + treeConfig.id,
773                                treeIconCls: "pimcore_" + treetype + "_customview_icon_" + treeConfig.id + " pimcore_icon_material",
774                                treeTitle: ts(treeConfig.name),
775                                parentPanel: treepanel,
776                                loaderBaseParams: {}
777                            }, treeConfig);
778                            pimcore.globalmanager.add("layout_" + treetype + "_tree_" + treeConfig.id, tree);
779
780                            treepanel.setHidden(false);
781                        }
782                    }
783                    break;
784            }
785
786
787            if (tree && treetype) {
788                locateConfigs[treetype].push({
789                    key: locateKey,
790                    side: side,
791                    tree: tree
792                });
793            }
794
795        }
796        pimcore.globalmanager.add("tree_locate_configs", locateConfigs);
797
798    }
799    catch (e) {
800        console.log(e);
801    }
802
803    layoutToolbar = new pimcore.layout.toolbar();
804    pimcore.globalmanager.add("layout_toolbar", layoutToolbar);
805
806
807    // check for activated maintenance-mode with this session-id
808    if (pimcore.settings.maintenance_mode) {
809        pimcore.helpers.showMaintenanceDisableButton();
810    }
811
812
813    if (user.isAllowed("dashboards") && pimcore.globalmanager.get("user").welcomescreen) {
814        window.setTimeout(function () {
815            layoutPortal = new pimcore.layout.portal();
816            pimcore.globalmanager.add("layout_portal_welcome", layoutPortal);
817        }, 1000);
818    }
819
820    pimcore.viewport.updateLayout();
821
822    // NOTE: the event pimcoreReady is fired in pimcore.layout.treepanelmanager
823    pimcore.layout.treepanelmanager.startup();
824
825    pimcore.helpers.registerKeyBindings(document);
826
827
828    if(pimcore.settings.twoFactorSetupRequired) {
829        Ext.Msg.show({
830            title: t('setup_two_factor'),
831            message: t('2fa_setup_message'),
832            buttons: Ext.Msg.OK,
833            icon: Ext.Msg.INFO,
834            fn: function(btn) {
835                pimcore.settings.profile.twoFactorSettings.prototype.openSetupWindow();
836            }
837        });
838    }
839
840    if(pimcore.currentuser.isPasswordReset) {
841        pimcore.helpers.openProfile();
842    }
843
844    // Quick Search
845    var quicksearchMap = new Ext.util.KeyMap({
846        target: document,
847        binding: [{
848            key:  Ext.event.Event.ESC,
849            fn: function () {
850                pimcore.helpers.hideQuickSearch();
851            }
852        }, {
853            key: Ext.event.Event.SPACE,
854            ctrl: true,
855            fn: function (keyCode, e) {
856                e.stopEvent();
857                pimcore.helpers.showQuickSearch();
858            }
859        }]
860    });
861
862    var quicksearchStore = new Ext.data.Store({
863        proxy: {
864            type: 'ajax',
865            url: '/admin/search/search/quicksearch',
866            reader: {
867                type: 'json',
868                rootProperty: 'data'
869            }
870        },
871        listeners: {
872            "beforeload": function (store) {
873                var previewEl = Ext.get('pimcore_quicksearch_preview');
874                if(previewEl) {
875                    previewEl.setHtml('');
876                }
877
878                store.getProxy().abort();
879            }
880        },
881        fields: ["id", 'type', "subtype", "className", "fullpath"]
882    });
883
884    var quickSearchTpl = new Ext.XTemplate(
885        '<tpl for=".">',
886            '<li role="option" unselectable="on" class="x-boundlist-item">' +
887                '<div class="list-icon {iconCls}"></div>' +
888                '<div class="list-path" title="{fullpath}">{fullpathList}</div>' +
889            '</li>',
890        '</tpl>'
891    );
892
893    var quicksearchContainer = Ext.get('pimcore_quicksearch');
894    var quickSearchCombo = Ext.create('Ext.form.ComboBox', {
895        width: 900,
896        hideTrigger: true,
897        border: false,
898        shadow: false,
899        tpl: quickSearchTpl,
900        listConfig: {
901            shadow: false,
902            border: false,
903            cls: 'pimcore_quicksearch_picker',
904            navigationModel: 'quicksearch.boundlist',
905            listeners: {
906                "highlightitem": function (view, node, opts) {
907                    // we use getAttribute() here instead of dataset -> IE11 has some strange issues with that in this case
908                    var record = quicksearchStore.getAt(node.getAttribute('data-recordIndex'));
909                    var previewHtml = record.get('preview');
910                    if(!previewHtml) {
911                        previewHtml = '<div class="no_preview">' + t('preview_not_available') + '</div>';
912                    }
913
914                    Ext.get('pimcore_quicksearch_preview').setHtml(previewHtml);
915                }
916            }
917        },
918        id: 'quickSearchCombo',
919        store: quicksearchStore,
920        loadingText: t('searching'),
921        queryDelay: 100,
922        minChars: 4,
923        renderTo: quicksearchContainer,
924        enableKeyEvents: true,
925        displayField: 'fullpath',
926        valueField: "id",
927        typeAhead: true,
928        listeners: {
929            "expand": function (combo) {
930                if(!document.getElementById('pimcore_quicksearch_preview')) {
931                    combo.getPicker().getEl().insertHtml('beforeEnd', '<div id="pimcore_quicksearch_preview"></div>');
932                }
933            },
934            "keyup": function (field) {
935                if(field.getValue()) {
936                    quicksearchContainer.addCls('filled');
937                }
938            },
939            "select": function (combo, record, index) {
940                pimcore.helpers.openElement(record.get('id'), record.get('type'), record.get('subtype'));
941                pimcore.helpers.hideQuickSearch();
942            }
943        }
944    });
945
946    Ext.getBody().on('click', function (event) {
947        // hide on click outside
948        if(quicksearchContainer && !quicksearchContainer.isAncestor(event.target)) {
949            var pickerEl = quickSearchCombo.getPicker().getEl();
950            if(!pickerEl || !pickerEl.isAncestor(event.target)) {
951                pimcore.helpers.hideQuickSearch();
952            }
953        }
954    });
955});
956
957
958pimcore["intervals"] = {};
959
960//add missing translation keys
961pimcore["intervals"]["translations_admin_missing"] = window.setInterval(function () {
962    var missingTranslations = pimcore.globalmanager.get("translations_admin_missing");
963    var addedTranslations = pimcore.globalmanager.get("translations_admin_added");
964    if (missingTranslations.length > 0) {
965        var thresholdIndex = 500;
966        var arraySurpassing = missingTranslations.length > thresholdIndex;
967        var sentTranslations = arraySurpassing ? missingTranslations.slice(0, thresholdIndex) : missingTranslations;
968        var params = Ext.encode(sentTranslations);
969        for (var i = 0; i < sentTranslations.length; i++) {
970            var translation = sentTranslations[i];
971            addedTranslations.push(translation);
972        }
973        var restMissingTranslations = missingTranslations.slice(thresholdIndex);
974        pimcore.globalmanager.add("translations_admin_missing", restMissingTranslations);
975        Ext.Ajax.request({
976            method: "POST",
977            url: "/admin/translation/add-admin-translation-keys",
978            params: {keys: params}
979        });
980    }
981}, 30000);
982
983// session renew
984pimcore["intervals"]["ping"] = window.setInterval(function () {
985    Ext.Ajax.request({
986        url: "/admin/misc/ping",
987        success: function (response) {
988
989            var data;
990
991            try {
992                data = Ext.decode(response.responseText);
993
994                if (data.success != true) {
995                    throw "session seems to be expired";
996                }
997            } catch (e) {
998                data = false;
999                pimcore.settings.showCloseConfirmation = false;
1000                window.location.href = "/admin/login?session_expired=true";
1001            }
1002
1003            if (pimcore.maintenanceWindow) {
1004                pimcore.maintenanceWindow.close();
1005                window.setTimeout(function () {
1006                    delete pimcore.maintenanceWindow;
1007                }, 2000);
1008                pimcore.viewport.updateLayout();
1009            }
1010
1011            if (data) {
1012                // here comes the check for maintenance mode, ...
1013            }
1014        },
1015        failure: function (response) {
1016            if (response.status != 503) {
1017                pimcore.settings.showCloseConfirmation = false;
1018                window.location.href = "/admin/login?session_expired=true&server_error=true";
1019            }
1020        }
1021    });
1022}, (pimcore.settings.session_gc_maxlifetime - 60) * 1000);
1023
1024
1025pimcore["intervals"]["checkNewNotification"] = window.setInterval(function (elt) {
1026    pimcore.notification.helper.updateFromServer();
1027}, 30000);
1028
1029// refreshes the layout
1030pimcore.registerNS("pimcore.layout.refresh");
1031pimcore.layout.refresh = function () {
1032    try {
1033        pimcore.viewport.updateLayout();
1034    }
1035    catch (e) {
1036    }
1037};
1038
1039// garbage collector
1040pimcore.helpers.unload = function () {
1041
1042};
1043