View Javadoc
1   /**
2    * This file Copyright (c) 2018 Magnolia International
3    * Ltd.  (http://www.magnolia-cms.com). All rights reserved.
4    *
5    *
6    * This file is dual-licensed under both the Magnolia
7    * Network Agreement and the GNU General Public License.
8    * You may elect to use one or the other of these licenses.
9    *
10   * This file is distributed in the hope that it will be
11   * useful, but AS-IS and WITHOUT ANY WARRANTY; without even the
12   * implied warranty of MERCHANTABILITY or FITNESS FOR A
13   * PARTICULAR PURPOSE, TITLE, or NONINFRINGEMENT.
14   * Redistribution, except as permitted by whichever of the GPL
15   * or MNA you select, is prohibited.
16   *
17   * 1. For the GPL license (GPL), you can redistribute and/or
18   * modify this file under the terms of the GNU General
19   * Public License, Version 3, as published by the Free Software
20   * Foundation.  You should have received a copy of the GNU
21   * General Public License, Version 3 along with this program;
22   * if not, write to the Free Software Foundation, Inc., 51
23   * Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
24   *
25   * 2. For the Magnolia Network Agreement (MNA), this file
26   * and the accompanying materials are made available under the
27   * terms of the MNA which accompanies this distribution, and
28   * is available at http://www.magnolia-cms.com/mna.html
29   *
30   * Any modifications to this file must keep this entire header
31   * intact.
32   *
33   */
34  package info.magnolia.poc;
35  
36  import static info.magnolia.ui.vaadin.gwt.client.shared.messagebubble.MessageBubbleAlignment.LEFT;
37  import static info.magnolia.ui.vaadin.gwt.client.shared.messagebubble.MessageBubbleType.*;
38  
39  import info.magnolia.icons.MagnoliaIcons;
40  import info.magnolia.ui.incub.LinkField;
41  import info.magnolia.ui.vaadin.extension.MessageBubble;
42  import info.magnolia.ui.vaadin.form.FormSection;
43  import info.magnolia.ui.vaadin.layout.SmallAppLayout;
44  
45  import java.util.Arrays;
46  
47  import javax.servlet.annotation.WebServlet;
48  
49  import org.apache.commons.lang3.StringUtils;
50  
51  import com.vaadin.annotations.Theme;
52  import com.vaadin.annotations.Title;
53  import com.vaadin.annotations.VaadinServletConfiguration;
54  import com.vaadin.annotations.Widgetset;
55  import com.vaadin.data.provider.DataProvider;
56  import com.vaadin.data.provider.ListDataProvider;
57  import com.vaadin.server.BrowserWindowOpener;
58  import com.vaadin.server.ExternalResource;
59  import com.vaadin.server.SerializablePredicate;
60  import com.vaadin.server.ThemeResource;
61  import com.vaadin.server.VaadinRequest;
62  import com.vaadin.server.VaadinServlet;
63  import com.vaadin.shared.ui.ContentMode;
64  import com.vaadin.shared.ui.grid.HeightMode;
65  import com.vaadin.ui.Button;
66  import com.vaadin.ui.ComboBox;
67  import com.vaadin.ui.Component;
68  import com.vaadin.ui.CssLayout;
69  import com.vaadin.ui.FormLayout;
70  import com.vaadin.ui.Grid;
71  import com.vaadin.ui.HorizontalLayout;
72  import com.vaadin.ui.Image;
73  import com.vaadin.ui.Label;
74  import com.vaadin.ui.NativeButton;
75  import com.vaadin.ui.RadioButtonGroup;
76  import com.vaadin.ui.TabSheet;
77  import com.vaadin.ui.TextArea;
78  import com.vaadin.ui.TextField;
79  import com.vaadin.ui.UI;
80  import com.vaadin.ui.VerticalLayout;
81  import com.vaadin.ui.components.grid.HeaderRow;
82  import com.vaadin.ui.renderers.AbstractRenderer;
83  import com.vaadin.ui.renderers.HtmlRenderer;
84  import com.vaadin.ui.themes.ValoTheme;
85  import com.vaadin.v7.ui.Table;
86  
87  @Theme("poctheme")
88  @Title("Magnolia 6 Resurface")
89  @Widgetset("info.magnolia.poc.Widgetset")
90  public class SmallAppLayoutUI extends UI {
91  
92      @WebServlet(value = "/smallapp/*", asyncSupported = true)
93      @VaadinServletConfiguration(productionMode = false, ui = SmallAppLayoutUI.class)
94      public static class Servlet extends VaadinServlet {
95      }
96  
97      private HorizontalLayout header = new HorizontalLayout();
98      private CssLayout viewPort = new CssLayout();
99  
100     @Override
101     protected void init(VaadinRequest request) {
102         header.setStyleName("header");
103         header.setSpacing(false);
104 
105         // Create logo
106         CssLayout logoWrapper = createLogoComponent();
107 
108         // Create finder bar
109         CssLayout finderBarContainer = new CssLayout();
110         finderBarContainer.setStyleName("periscope-wrapper");
111 
112         Component finderBar = createFinderBar();
113 
114         finderBarContainer.addComponent(finderBar);
115 
116         // Create tasks indicator
117         CssLayout tasksWrapper = new CssLayout();
118         tasksWrapper.setStyleName("tasks-wrapper");
119         Component taskIndicator = createIndicatorComponent("Tasks", "23", "green");
120         tasksWrapper.addComponent(taskIndicator);
121 
122         // Create message indicator
123         CssLayout messageWrapper = new CssLayout();
124         messageWrapper.setStyleName("messages-wrapper");
125         Component messageIndicator = createIndicatorComponent("Messages", "02", "green");
126         messageWrapper.addComponent(messageIndicator);
127 
128         // Create profile component
129         Component profileWrapper = createProfileComponent();
130         profileWrapper.setStyleName("profile-wrapper");
131 
132         header.addComponents(logoWrapper, finderBarContainer, tasksWrapper, messageWrapper, profileWrapper);
133 
134         viewPort.setStyleName("viewport");
135         viewPort.setSizeFull();
136 
137         Component tabSheet = createTabSheetComponent();
138         viewPort.addComponents(tabSheet);
139 
140 
141         final VerticalLayout layout = new VerticalLayout();
142         layout.setStyleName("main-wrapper");
143         layout.setSpacing(false);
144         layout.addComponents(header, viewPort);
145         layout.setMargin(false);
146         layout.setExpandRatio(header, 0f);
147         layout.setExpandRatio(viewPort, 1f);
148         layout.setSizeFull();
149 
150         setContent(layout);
151     }
152 
153 
154     private CssLayout createLogoComponent() {
155         CssLayout logoWrapper = new CssLayout();
156         logoWrapper.setStyleName("logo-wrapper");
157 
158         ThemeResource resource = new ThemeResource("img/logo-magnolia.svg");
159         // Show the image in the application
160         Image image = new Image("Magnolia logo", resource);
161         image.addStyleName("header-component");
162         logoWrapper.addComponent(image);
163         return logoWrapper;
164     }
165 
166     private HorizontalLayout createProfileComponent() {
167         HorizontalLayout profileWrapper = new HorizontalLayout();
168         profileWrapper.setSpacing(false);
169         profileWrapper.setMargin(false);
170 
171         Label avatar = new Label();
172         avatar.setContentMode(ContentMode.HTML);
173         avatar.addStyleName("header-component");
174         avatar.setValue("<span class='indicator number icon-user-role'></span>");
175         profileWrapper.addComponent(avatar);
176 
177         Component profileComponent = createHeaderComponent("public-01", "INT");
178         profileWrapper.addComponent(profileComponent);
179         return profileWrapper;
180     }
181 
182     private HorizontalLayout createFinderBar() {
183         HorizontalLayout finderBar = new HorizontalLayout();
184         finderBar.addStyleName("header-component");
185         finderBar.setSpacing(false);
186         finderBar.setMargin(false);
187         finderBar.setSizeFull();
188         Button shellButton = new Button();
189         shellButton.addStyleName("btn-shell icon-appslauncher btn-appslauncher");
190         finderBar.addComponent(shellButton);
191         finderBar.setExpandRatio(shellButton, 0f);
192 
193         CssLayout searchField = new CssLayout();
194         searchField.setStyleName("search-field");
195         TextField textField = new TextField();
196         textField.addStyleNames("search-textfield", "heading-2");
197         textField.setPlaceholder("Type to find");
198         searchField.addComponent(textField);
199         Label searchIcon = new Label();
200         searchIcon.setStyleName("icon-search");
201         searchField.addComponent(searchIcon);
202 
203         finderBar.addComponent(searchField);
204         finderBar.setExpandRatio(searchField, 1f);
205 
206 
207         Button voiceButton = new Button();
208         voiceButton.addStyleName("btn-shell icon-target-app btn-voice");
209         finderBar.addComponent(voiceButton);
210         finderBar.setExpandRatio(voiceButton, 0f);
211 
212         return finderBar;
213     }
214 
215     private Component createIndicatorComponent(String label, String value, String status) {
216         return createHeaderComponent(label, value + "<span class='status icon-status-" + status + " color-" + status + "'></span>");
217     }
218 
219     private Component createHeaderComponent(String label, String value) {
220 
221         VerticalLayout tasksComponent = new VerticalLayout();
222         tasksComponent.setSpacing(false);
223         tasksComponent.setMargin(false);
224         tasksComponent.setStyleName("header-component");
225         Label taskNumber = new Label();
226         taskNumber.addStyleName("indicator heading-2");
227         taskNumber.setValue(value);
228         taskNumber.setContentMode(ContentMode.HTML);
229         Label taskLabel = new Label(label);
230         taskLabel.addStyleNames("text-tiny");
231         tasksComponent.addComponents(taskNumber, taskLabel);
232 
233         return tasksComponent;
234     }
235 
236     private Component createTabSheetComponent() {
237 
238         TabSheet tabSheetComponent = new TabSheet();
239         tabSheetComponent.addStyleName(ValoTheme.TABSHEET_FRAMED);
240         tabSheetComponent.addStyleName("apps");
241         tabSheetComponent.setSizeFull();
242 
243         SmallAppLayout smallAppLayout = new SmallAppLayout();
244         smallAppLayout.setDescription("Introductory description");
245         smallAppLayout.addSection(createSmallAppFormLayout(), "Title 1 / Primary title");
246         tabSheetComponent.addTab(smallAppLayout, "Form Layout");
247 
248         SmallAppLayout aboutMagnolia = new SmallAppLayout();
249         aboutMagnolia.setDescription("The about app shows an overview of the installed Magnolia version and the environment it runs in.");
250         aboutMagnolia.addSection(createAboutMagnoliaInstallationInformationSection(), "Installation information");
251         aboutMagnolia.addSection(createAboutMagnoliaLicenseInformationSection(), "License information");
252         tabSheetComponent.addTab(aboutMagnolia, "About Magnolia", MagnoliaIcons.ASSETS_APP);
253 
254         SmallAppLayout reportIssue = new SmallAppLayout();
255         reportIssue.setDescription("Use the options below to report an issue.");
256         reportIssue.addSection(createReportIssueSection(), "JIRA issues");
257         TabSheet.Tab repportIssueTab = tabSheetComponent.addTab(reportIssue, "Report an issue");
258         repportIssueTab.setClosable(true);
259 
260         SmallAppLayout configIssue = new SmallAppLayout();
261         configIssue.setDescription("Better to write something here…");
262         configIssue.addSection(createConfigInfoSection(), "Server configuration page");
263         TabSheet.Tab configIssueTab = tabSheetComponent.addTab(configIssue, "Config info");
264         configIssueTab.setClosable(true);
265 
266         SmallAppLayout publishing = new SmallAppLayout();
267         publishing.setDescription("Use the tools below to generate a new key or clean up mgnlSystem workspace.");
268         publishing.addSection(createPublishinKeySection(), "Generate new key");
269         publishing.addSection(createCleanMgnlSystemWorkspaceSection(), "Clean mgnlSystem workspace");
270         TabSheet.Tab publishingToolsTab = tabSheetComponent.addTab(publishing, "Publishing Tools");
271         publishingToolsTab.setClosable(true);
272 
273         SmallAppLayout publishingMonitor = new SmallAppLayout();
274         publishingMonitor.setDescription("Better to write something here…");
275         publishingMonitor.addSection(createPublishinMonitorOverviewSection(),"Monitor");
276         publishingMonitor.addSection(createPublishingPerWorkspaceSection());
277         publishingMonitor.addSection(createPublicInstaceResponceSection());
278         publishingMonitor.addSection(createPublishingLogSection());
279         publishingMonitor.addSection(createPublishingErrorLogSection());
280         TabSheet.Tab publishingMonitorTab = tabSheetComponent.addTab(publishingMonitor, "Publishing Monitor");
281         publishingMonitorTab.setClosable(true);
282 
283         SmallAppLayout mailVerifySetup = new SmallAppLayout();
284         mailVerifySetup.setDescription("Use the tools below to send test mails to verify your mail set up and mail settings.");
285         mailVerifySetup.addSection(createVerifyMailSettingSection(), "Verify mail setting");
286         mailVerifySetup.addSection(createVerifyMailTemplatesSection(), "Message templates");
287         tabSheetComponent.addTab(mailVerifySetup, "Verify Setup");
288 
289         SmallAppLayout cacheTools = new SmallAppLayout();
290         cacheTools.setDescription("We might want to write something here…");
291         cacheTools.addSection(createCacheInformationSection());
292         cacheTools.addSection(createFlushCacheByUuidSection());
293         cacheTools.addSection(createFlushCacheByNameSection());
294         cacheTools.addSection(createFlushCacheSection());
295         tabSheetComponent.addTab(cacheTools, "Cache Tools");
296 
297         return tabSheetComponent;
298     }
299 
300     private Component createSmallAppFormLayout() {
301         FormLayout layout = new FormLayout();
302         layout.addComponent(initLabel(null, "Secondary title", "fieldset-title"));
303         layout.addComponent(initLabel("Static field", "Lorem ipsum"));
304         layout.addComponent(initTextField("Field types", ""));
305         layout.addComponent(initTextField("Field types", TextComponentUI.TEXT_SHORT));
306         layout.addComponent(initTextArea("Field types", TextComponentUI.TEXT_2_LINES, 2));
307         layout.addComponent(initTextArea("Field types", TextComponentUI.TEXT_3_LINES, 3));
308         ComboBox<String> selectField = new ComboBox<>("Select field", Arrays.asList("Option 1", "Option2", "Option3"));
309         selectField.setPlaceholder("Select...");
310         layout.addComponent(selectField);
311         layout.addComponent(initLabel(null, "Plain text… This article covers the basics of Astrology and how they are inter-related. Astrology is defined as ‘the art or practice of determining the supposed influences of the planets and their motions on human affairs and human disposition’. From this practice a horoscope can be produced a diagram (or chart) of the relative positions of planets and signs of the Zodiac at a specific time, usually the time of birth. A forecast can then be produced."));
312 
313         HorizontalLayout controls = new HorizontalLayout(initButton("Primary button", "commit"), initButton("Secondary button", "secondary-button"));
314         MessageBubble infoBubble = MessageBubble.extend(controls);
315         infoBubble.setMessageType(INFO);
316         infoBubble.setTitle("Your running with a trial license");
317         infoBubble.setMessage("Your trial period ends in 40 days. After that all enterprise-only features will be disabled. Please contact us for full license.");
318         MessageBubble warnBubble = MessageBubble.extend(controls);
319         warnBubble.setMessageType(WARNING);
320         warnBubble.setTitle("Your license will expire in 10 days");
321         warnBubble.setMessage("All Enterprise-only features will be disabled. Make sure you renew in-time or request a temporary license.");
322         MessageBubble errorBubble = MessageBubble.extend(controls);
323         errorBubble.setMessageType(ERROR);
324         errorBubble.setTitle("Your product license has expired");
325         errorBubble.setMessage("All Enterprise-only features have been disabled. Please contact us for a renewal or a temporary license.");
326         layout.addComponent(controls);
327 
328         HorizontalLayout formButtons = new HorizontalLayout(new Button("Form Button"), new Button("Form Button"), new Button("Form Button"));
329         layout.addComponent(formButtons);
330 
331         ListDataProvider<FakeGridBean> listDataProvider = DataProvider.ofItems(
332                 new FakeGridBean("01", "Lorem ipsum", "Lorem ipsum"),
333                 new FakeGridBean("02", "uLorem ipsum", "Lorem ipsum"),
334                 new FakeGridBean("02", "Lorem ipsum", "Lorem ipsum"),
335                 new FakeGridBean("...", "Lorem ipsum", "Lorem ipsum"));
336         Grid<FakeGridBean> grid = new Grid<>(FakeGridBean.class);
337         grid.setDataProvider(listDataProvider);
338         grid.setWidth(100, Unit.PERCENTAGE);
339         grid.setHeightByRows(listDataProvider.getItems().size());
340         grid.getColumn("firstColumn").setCaption("Column 1");
341         grid.getColumn("secondColumn").setCaption("Column 2");
342         grid.getColumn("thirdColumn").setCaption("Column 3");
343         layout.addComponent(grid);
344 
345         return layout;
346     }
347 
348     private Component createAboutMagnoliaInstallationInformationSection() {
349         FormLayout layout = new FormLayout();
350         layout.addComponent(initLabel(null, "Magnolia", "fieldset-title"));
351         layout.addComponent(initLabel("Edition", "Enterprise Edition – Professional"));
352         layout.addComponent(initLabel("Version / Bundle", "6.0"));
353         layout.addComponent(initLabel("Instance", "Author instance"));
354         layout.addComponent(initLabel(null, "Environment", "fieldset-title"));
355         layout.addComponent(initLabel("Operating system", "Dealing With Technical Support 10 Useful Tips"));
356         layout.addComponent(initLabel("Java version", "V7 Digital Photo Printing"));
357         layout.addComponent(initLabel("Application server", "Live Poker How To Win Tournament Games"));
358         layout.addComponent(initLabel(null, "Plain text", "fieldset-title"));
359         layout.addComponent(initLabel(null, "Nullam quis risus eget urna mollis ornare vel eu leo. Sed posuere consec tetur est at lobortis. Cras justo odio, dapibus ac facilisis in, egestas eget quam. Duis mollis, est non commodo luctus, nisi erat porttitor ligula, eget lacinia odio sem nec elit. Etiam porta"));
360 
361         return layout;
362     }
363 
364     private Component createAboutMagnoliaLicenseInformationSection() {
365         FormLayout layout = new FormLayout();
366         layout.addComponent(initLabel("Owner", "demo@magnolia-cms.com"));
367         Label expirationField = initLabel("Expiration date", "Juli 31, 2018 ");
368         layout.addComponent(expirationField);
369         MessageBubble infoBubble = MessageBubble.extend(expirationField);
370         infoBubble.setAlignment(LEFT);
371         infoBubble.setMessageType(INFO);
372         infoBubble.setTitle("Your running with a trial license");
373         infoBubble.setMessage("Your trial period ends in 40 days. After that all enterprise-only features will be disabled. Please contact us for full license.");
374 
375         HorizontalLayout licenseControls = new HorizontalLayout();
376         licenseControls.setSpacing(true);
377         licenseControls.addStyleName("spacer");
378         NativeButton enterLicenseButton = new NativeButton("Enter license info");
379         enterLicenseButton.addStyleName("magnoliabutton commit");
380         Button contactButton = initButton("Contact us", "secondary-button");
381         BrowserWindowOpener opener = new BrowserWindowOpener(new ExternalResource("http://www.magnolia-cms.com/license-management"));
382         opener.extend(contactButton);
383         licenseControls.addComponents(enterLicenseButton, contactButton);
384         layout.addComponent(licenseControls);
385         return layout;
386     }
387 
388     private Component createReportIssueSection() {
389         VerticalLayout contentLayout = new VerticalLayout();
390 
391         HorizontalLayout buttonsLayout = new HorizontalLayout();
392         buttonsLayout.addComponents(initNativeButton("Installation and Migration", "magnoliabutton"));
393         buttonsLayout.addComponents(initNativeButton("Support request", "magnoliabutton"));
394         buttonsLayout.addComponents(initNativeButton("Development support request", "magnoliabutton"));
395         buttonsLayout.addComponents(initNativeButton("Magnolia malfunction", "magnoliabutton"));
396 
397         ListDataProvider<FakeGridBean> listDataProvider = DataProvider.ofItems(
398                 new FakeGridBean("SUPPORT-8805", "JCR query performance for big workspace", "Open"),
399                 new FakeGridBean("SUPPORT-8805", "unable to add language code in sitemap XML file generated from Sitemap application", "Waiting for customer information"),
400                 new FakeGridBean("SUPPORT-8806", "Lorem ipsum", "In progress"),
401                 new FakeGridBean("MAGNOLIA-7252", "Add support for Tomcat 9", "Closed"));
402         Grid<FakeGridBean> issuesGrid = new Grid<>(FakeGridBean.class);
403         issuesGrid.setWidth(100, Unit.PERCENTAGE);
404         issuesGrid.setHeightMode(HeightMode.ROW);
405         issuesGrid.setHeightByRows(listDataProvider.getItems().size());
406         issuesGrid.setDataProvider(listDataProvider);
407         issuesGrid.setColumnOrder("firstColumn", "secondColumn", "thirdColumn");
408         issuesGrid.getColumn("firstColumn")
409                 .setCaption("Key")
410                 .setWidth(150);
411         issuesGrid.getColumn("secondColumn")
412                 .setCaption("Summary")
413                 .setExpandRatio(2)
414                 .setSortable(false);
415         issuesGrid.getColumn("thirdColumn")
416                 .setCaption("Status")
417                 .setExpandRatio(1);
418 
419         contentLayout.addComponents(buttonsLayout, issuesGrid);
420         return contentLayout;
421     }
422 
423     private Component createConfigInfoSection() {
424         VerticalLayout layout = new VerticalLayout();
425 
426         layout.addComponent(initLabel(null, "General Magnolia Server Data", "fieldset-title"));
427         layout.addComponent(initLabel(null, "Is admin server: true"));
428         layout.addComponent(initLabel(null, "General Magnolia System Data", "fieldset-title"));
429 
430         ListDataProvider<ConfigBean> listDataProvider = DataProvider.ofItems(
431                 new ConfigBean("awt.toolkit", "sun.awt.X11.XToolkit"),
432                 new ConfigBean("catalina.base", "/var/lib/demoauthor-a/tomcat"),
433                 new ConfigBean("catalina.home", "/usr/share/tomcat8"),
434                 new ConfigBean("java.awt.graphicsenv", "sun.awt.X11GraphicsEnvironment"),
435                 new ConfigBean("java.ext.dirs", "/usr/lib/jvm/java-8-openjdk-amd64/jre/lib/endorsed"),
436                 new ConfigBean("info.magnolia.imaging.operations.load.ImageDecoder", "info.magnolia.imaging.operations.load.DefaultImageIOImageDecoder"));
437         Grid<ConfigBean> grid = new Grid<>(ConfigBean.class);
438         grid.setSizeFull();
439         grid.setDataProvider(listDataProvider);
440         grid.setSelectionMode(Grid.SelectionMode.NONE);
441         grid.setColumnOrder("config", "value");
442         grid.getColumn("config")
443                 .setCaption("Configuration")
444                 .setExpandRatio(0);
445 
446         grid.getColumn("value")
447                 .setCaption("Value")
448                 .setExpandRatio(2);
449 
450         HeaderRow filterRow = grid.appendHeaderRow();
451 
452         CssLayout filterConfigLayout = new CssLayout();
453         filterConfigLayout.addStyleName("search-field");
454         TextField filterConfigField = new TextField();
455         filterConfigField.setPlaceholder("Search...");
456         filterConfigLayout.addComponents(filterConfigField, initSearchIconLabel());
457         filterRow.getCell("config").setComponent(filterConfigLayout);
458 
459         CssLayout filterValueLayout = new CssLayout();
460         filterValueLayout.addStyleName("search-field");
461         TextField filterValueField = new TextField();
462         filterValueField.setPlaceholder("Search...");
463         filterValueLayout.addComponents(filterValueField, initSearchIconLabel());
464         filterRow.getCell("value").setComponent(filterValueLayout);
465 
466         filterConfigField.addValueChangeListener(event ->
467                 listDataProvider.setFilter((SerializablePredicate<ConfigBean>) configBean -> configBean.getConfig().toLowerCase().contains(filterConfigField.getValue().toLowerCase()) && configBean.getValue().toLowerCase().contains(filterValueField.getValue().toLowerCase()))
468         );
469         filterValueField.addValueChangeListener(event ->
470                 listDataProvider.setFilter((SerializablePredicate<ConfigBean>) configBean -> configBean.getConfig().toLowerCase().contains(filterConfigField.getValue().toLowerCase()) && configBean.getValue().toLowerCase().contains(filterValueField.getValue().toLowerCase()))
471         );
472 
473         layout.addComponent(grid);
474 
475         return layout;
476     }
477 
478     private Component createPublishinKeySection() {
479         FormLayout formLayout = new FormLayout();
480         formLayout.addComponent(initLabel(null, "You can copy the initial public key directly to all public instances under config:/server… property or it will be transferred automatically to all configured public instances upon first publishing. A newly generated public key needs to be copied to all public instances. It is not transferred automatically on publishing as is the case with the initial key. When a new key is generated, the publicKey node cannot be published to the public instance as at this point a mismatch exists between the keys on author and public."));
481         formLayout.addComponent(initLabel(null, "Generate new key", "fieldset-title"));
482         formLayout.addComponent(initTextField("Key length (min. 512 max.1024)", "1024"));
483         formLayout.addComponent(initButton("Generate new key", "commit"));
484         formLayout.addComponent(initLabel(null, "Current public key", "fieldset-title"));
485         TextArea currentKey = initTextArea(null, "30819F300D06092A864886F70D010101050003818D00308189028181009D368CB3D6E777879124F2E6A232E5A321BBFFFE1FDEB939BD7D50DB8DFAADC4A60AABD46FDE2D6A8DFB89C5AD1A7774167DFFE9AABA58352987883AC2D275297F4D673B8D42C4FC88C3FA550B2372D00DEBE4D260C1BC224EB45B6763175FFA1FDCB32F7C1B89C1E80FF45686BB1E5EE7B3E83C825F4B53704AA03F0676B0430203010001", 5);
486         currentKey.setReadOnly(true);
487         formLayout.addComponent(currentKey);
488         return formLayout;
489     }
490 
491     private Component createCleanMgnlSystemWorkspaceSection() {
492         FormLayout formLayout = new FormLayout();
493         formLayout.addComponent(initLabel(null, "Clean mgnlWorkspace ", "fieldset-title"));
494         formLayout.addComponent(initLabel(null, "NOTE: mgnlSystem workspace is necessary only on Public instances"));
495         formLayout.addComponent(initButton("Clean mgnlSystem workspace", "commit"));
496         return formLayout;
497     }
498 
499     private Component createPublishinMonitorOverviewSection() {
500         FormLayout layout = new FormLayout();
501         layout.addComponent(initLabel(null, "Overview", "fieldset-title"));
502         layout.addComponent(initLabel("Last start", "06/19/2018 11:03:07"));
503         layout.addComponent(initLabel("Publishing requests", "0"));
504         layout.addComponent(initLabel("Unpublishing requests", "0"));
505         layout.addComponent(initLabel("Number of errors", "0"));
506         layout.addComponent(initLabel("Committed transactions", "0"));
507         layout.addComponent(initLabel("Rolled back transactions", "0"));
508         layout.addComponent(initLabel("Size of published content", "0 KB"));
509         layout.addComponent(initLabel("Time needed for publishing", "0.0 sec"));
510         return layout;
511     }
512 
513     private Component createPublishingPerWorkspaceSection() {
514         FormLayout layout = new FormLayout();
515         layout.addComponent(initLabel(null, "Publishing requests per workspace", "fieldset-title"));
516         layout.addComponent(initLabel("dam", "1"));
517         layout.addComponent(initLabel("website", "3"));
518         return layout;
519     }
520 
521     private Component createPublicInstaceResponceSection() {
522         VerticalLayout verticalLayout = new VerticalLayout();
523         verticalLayout.addComponent(initLabel(null, "Public instance response", "fieldset-title"));
524         verticalLayout.addComponent(initLabel(null, "No publishing done yet."));
525         return verticalLayout;
526     }
527 
528     private Component createPublishingLogSection() {
529         VerticalLayout verticalLayout = new VerticalLayout();
530         verticalLayout.addComponent(initLabel(null, "Publishing log", "fieldset-title"));
531 
532         ListDataProvider<PublishingLogBean> listDataProvider = DataProvider.ofItems(
533                 new PublishingLogBean("<span class=\"icon-error\"></span>", "09/12/2018 11:04:40", "superuser", "website", "/travel/tour", "magnoliaPublic"),
534                 new PublishingLogBean("<span class=\"icon-error\"></span>", "09/12/2018 11:04:40", "eric", "website", "/travel/tour", "magnoliaPublic"),
535                 new PublishingLogBean("<span class=\"icon-error\"></span>", "09/12/2018 11:04:40", "peter", "website", "/travel/tour", "magnoliaPublic"),
536                 new PublishingLogBean("<span class=\"icon-error\"></span>", "09/12/2018 11:04:40", "superuser", "website", "/travel/tour", "magnoliaPublic"));
537         Grid<PublishingLogBean> grid = new Grid<>(PublishingLogBean.class);
538         grid.setSizeFull();
539         grid.setDataProvider(listDataProvider);
540         grid.setSelectionMode(Grid.SelectionMode.NONE);
541         grid.setColumnOrder("label", "date", "user", "workspace", "path", "subscriber");
542         grid.getColumn("label")
543                 .setStyleGenerator(item -> "v-align-center")
544                 .setRenderer((AbstractRenderer) new HtmlRenderer())
545                 .setCaption(StringUtils.EMPTY)
546                 .setWidth(100);
547 
548         HeaderRow filterRow = grid.appendHeaderRow();
549         CssLayout filterUserLayout = new CssLayout();
550         filterUserLayout.addStyleName("search-field");
551         TextField filterUserField = new TextField();
552         filterUserField.setPlaceholder("Search...");
553         filterUserLayout.addComponents(filterUserField, initSearchIconLabel());
554         filterRow.getCell("user").setComponent(filterUserLayout);
555         filterUserField.addValueChangeListener(event ->
556                 listDataProvider.setFilter(PublishingLogBean::getUser, s -> StringUtils.isBlank(event.getValue()) || s.equals(event.getValue()))
557         );
558 
559         verticalLayout.addComponent(grid);
560 
561         return verticalLayout;
562     }
563 
564     private Component createPublishingErrorLogSection() {
565         VerticalLayout verticalLayout = new VerticalLayout();
566         verticalLayout.addComponent(initLabel(null, "Error log", "fieldset-title"));
567         verticalLayout.addComponent(initLabel(null, "Error log is empty."));
568         return verticalLayout;
569     }
570 
571 
572     private Component createVerifyMailSettingSection() {
573         CssLayout layout = new CssLayout();
574 
575         FormSection formSection = new FormSection();
576         formSection.addComponent(initLabel("", "Verify the current mail settings", "fieldset-title"));
577         formSection.addComponent(initLabel("", "A pre-configured mail and optional mail attachment will be sent the email address configured in your user profile."));
578         RadioButtonGroup<String> radioButtonGroup = new RadioButtonGroup<>();
579         radioButtonGroup.setItems("Send a mail with plain text", "Send a mail with rich text");
580         formSection.addComponent(radioButtonGroup);
581         LinkField linkField = new LinkField();
582         linkField.setButtonCaptionNew("Select new");
583         linkField.setCaption("Attachment");
584         formSection.addComponent(linkField);
585         CssLayout form = new CssLayout(formSection);
586         form.setStyleName("form-panel v-magnolia-form");
587 
588         CssLayout buttonLayout = new CssLayout();
589         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
590         buttonLayout.addComponent(initButton("Send test mail", "commit"));
591 
592         layout.addComponents(form, buttonLayout);
593         return layout;
594     }
595 
596     private Component createVerifyMailTemplatesSection() {
597         CssLayout layout = new CssLayout();
598 
599         FormSection formSection = new FormSection();
600         formSection.addComponent(initLabel("", "Verify message templates", "fieldset-title"));
601         formSection.addComponent(initLabel("", "Mail message templates are typically used by forms on a web page to send the data they contain to a recipient. The test mail will be sent to the email address configured in your user profile."));
602         ComboBox<String> comboBox = new ComboBox<>();
603         comboBox.setCaption("Message templates");
604         comboBox.setItems("pageCommentsNotification", "testFreemarker", "workflowNotification");
605         comboBox.setEmptySelectionAllowed(false);
606         comboBox.setPlaceholder("Select...");
607         formSection.addComponent(comboBox);
608         formSection.addComponent(initTextArea("Data to send", "", 5));
609         CssLayout form = new CssLayout(formSection);
610         form.setStyleName("form-panel v-magnolia-form");
611 
612         CssLayout buttonLayout = new CssLayout();
613         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
614         buttonLayout.addComponent(initButton("Send test mail", "commit"));
615 
616         layout.addComponents(form, buttonLayout);
617         return layout;
618     }
619 
620     private Component createCacheInformationSection() {
621         CssLayout layout = new CssLayout();
622 
623         layout.addComponents(initLabel(null, "Cache information", "section-title"));
624 
625         FormLayout formLayout = new FormLayout();
626         formLayout.setSpacing(true);
627         formLayout.setMargin(false);
628         Table cacheSizeTable = new Table();
629         cacheSizeTable.setSelectable(false);
630         cacheSizeTable.setWidth("100%");
631         cacheSizeTable.addContainerProperty("Cache", String.class, null);
632         cacheSizeTable.addContainerProperty("Number of elements", Integer.class, null);
633         cacheSizeTable.addItem(new Object[]{"defaultPageCache", 100}, "defaultPageCache 100");
634         cacheSizeTable.addItem(new Object[]{"uuid-key-mapping", 10}, "uuid-key-mapping 10");
635         cacheSizeTable.addItem(new Object[]{"defaultDamCache", 100}, "defaultDamCache 101");
636         cacheSizeTable.addItem(new Object[]{"defaultConfigCache", 10}, "defaultConfigCache 11");
637         cacheSizeTable.setPageLength(cacheSizeTable.size());
638         formLayout.addComponent(cacheSizeTable);
639         layout.addComponents(formLayout);
640 
641         CssLayout buttonLayout = new CssLayout();
642         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
643         buttonLayout.addComponent(initButton("Refresh", "commit"));
644         layout.addComponents(buttonLayout);
645 
646         return layout;
647     }
648 
649     private Component createFlushCacheByUuidSection() {
650         CssLayout layout = new CssLayout();
651 
652         layout.addComponents(initLabel(null, "Flush from cache by UUID", "section-title"));
653 
654         FormSection formSection = new FormSection();
655         formSection.addComponent(initTextField("UUID", ""));
656         ComboBox<String> comboBox = new ComboBox<>();
657         comboBox.setItems("dam", "website", "config");
658         comboBox.setSelectedItem("dam");
659         comboBox.setEmptySelectionAllowed(false);
660         formSection.addComponent(comboBox);
661         CssLayout form = new CssLayout(formSection);
662         form.setStyleName("form-panel v-magnolia-form");
663 
664         CssLayout buttonLayout = new CssLayout();
665         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
666         buttonLayout.addComponent(initButton("Flush UUID", "commit"));
667 
668         layout.addComponents(form, buttonLayout);
669         return layout;
670     }
671 
672     private Component createFlushCacheByNameSection() {
673         CssLayout layout = new CssLayout();
674 
675         layout.addComponents(initLabel(null, "Flush cache by name", "section-title"));
676 
677         FormSection formSection = new FormSection();
678         ComboBox<String> comboBox = new ComboBox<>();
679         comboBox.setItems("defaultPageCache", "uuid-key-mapping");
680         comboBox.setSelectedItem("defaultPageCache");
681         comboBox.setEmptySelectionAllowed(false);
682         formSection.addComponent(comboBox);
683         CssLayout form = new CssLayout(formSection);
684         form.setStyleName("form-panel v-magnolia-form");
685 
686         CssLayout buttonLayout = new CssLayout();
687         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
688         buttonLayout.addComponent(initButton("Flush Cache", "commit"));
689 
690         layout.addComponents(form, buttonLayout);
691         return layout;
692     }
693 
694     private Component createFlushCacheSection() {
695         CssLayout layout = new CssLayout();
696 
697         layout.addComponents(initLabel(null, "Flush all caches", "section-title"));
698 
699         CssLayout buttonLayout = new CssLayout();
700         buttonLayout.addStyleName("v-csslayout-smallapp-actions");
701         buttonLayout.addComponent(initButton("Flush All", "commit"));
702 
703         layout.addComponents(buttonLayout);
704         return layout;
705     }
706 
707     private Label initLabel(String caption, String text) {
708         return initLabel(caption, text, null);
709     }
710 
711     private Label initLabel(String caption, String text, String styleName) {
712         Label label = new Label();
713         label.setCaption(caption);
714         label.setValue(text);
715         label.addStyleName(styleName);
716         return label;
717     }
718 
719     private Label initSearchIconLabel() {
720         Label label = new Label();
721         label.addStyleName("icon-search");
722         return label;
723     }
724 
725     private TextField initTextField(String caption, String text) {
726         TextField textField = new TextField();
727         textField.setCaption(caption);
728         textField.setValue(text);
729         return textField;
730     }
731 
732     private TextArea initTextArea(String caption, String text, int rows) {
733         TextArea textArea = new TextArea();
734         textArea.setCaption(caption);
735         textArea.setValue(text);
736         textArea.setRows(rows);
737         return textArea;
738     }
739 
740     private Button initButton(String caption, String styleName) {
741         Button button = new Button(caption);
742         button.addStyleName(styleName);
743         return button;
744     }
745 
746     private NativeButton initNativeButton(String caption, String styleName) {
747         NativeButton nativeButton = new NativeButton(caption);
748         nativeButton.addStyleName(styleName);
749         return nativeButton;
750     }
751 
752     public static class FakeGridBean {
753         private final String firstColumn;
754         private final String secondColumn;
755         private final String thirdColumn;
756 
757         public FakeGridBean(final String firstColumn, final String secondColumn, final String thirdColumn) {
758             this.firstColumn = firstColumn;
759             this.secondColumn = secondColumn;
760             this.thirdColumn = thirdColumn;
761         }
762 
763         public String getFirstColumn() {
764             return firstColumn;
765         }
766 
767         public String getSecondColumn() {
768             return secondColumn;
769         }
770 
771         public String getThirdColumn() {
772             return thirdColumn;
773         }
774     }
775 
776     public static class ConfigBean {
777         private final String config;
778         private final String value;
779 
780         public ConfigBean(final String config, final String value) {
781             this.config = config;
782             this.value = value;
783         }
784 
785         public String getConfig() {
786             return config;
787         }
788 
789         public String getValue() {
790             return value;
791         }
792     }
793 
794     public static class PublishingLogBean {
795         private final String label;
796         private final String date;
797         private final String user;
798         private final String workspace;
799         private final String path;
800         private final String subscriber;
801 
802         public PublishingLogBean(String label, String date, String user, String workspace, String path, String subscriber) {
803             this.label = label;
804             this.date = date;
805             this.user = user;
806             this.workspace = workspace;
807             this.path = path;
808             this.subscriber = subscriber;
809         }
810 
811         public String getLabel() {
812             return label;
813         }
814 
815         public String getDate() {
816             return date;
817         }
818 
819         public String getUser() {
820             return user;
821         }
822 
823         public String getWorkspace() {
824             return workspace;
825         }
826 
827         public String getPath() {
828             return path;
829         }
830 
831         public String getSubscriber() {
832             return subscriber;
833         }
834     }
835 }