tmf: Bug 497038: Custom parser field names conflict with built-in tags
[deliverable/tracecompass.git] / tmf / org.eclipse.tracecompass.tmf.ui / src / org / eclipse / tracecompass / internal / tmf / ui / parsers / wizards / CustomXmlParserInputWizardPage.java
1 /*******************************************************************************
2 * Copyright (c) 2010, 2016 Ericsson
3 *
4 * All rights reserved. This program and the accompanying materials are
5 * made available under the terms of the Eclipse Public License v1.0 which
6 * accompanies this distribution, and is available at
7 * http://www.eclipse.org/legal/epl-v10.html
8 *
9 * Contributors:
10 * Patrick Tasse - Initial API and implementation
11 *******************************************************************************/
12
13 package org.eclipse.tracecompass.internal.tmf.ui.parsers.wizards;
14
15 import java.io.BufferedReader;
16 import java.io.ByteArrayInputStream;
17 import java.io.IOException;
18 import java.io.InputStream;
19 import java.io.InputStreamReader;
20 import java.net.URL;
21 import java.text.ParseException;
22 import java.util.AbstractMap.SimpleEntry;
23 import java.util.ArrayList;
24 import java.util.List;
25 import java.util.Map.Entry;
26
27 import javax.xml.parsers.DocumentBuilder;
28 import javax.xml.parsers.DocumentBuilderFactory;
29 import javax.xml.parsers.ParserConfigurationException;
30
31 import org.eclipse.core.resources.IFile;
32 import org.eclipse.core.runtime.CoreException;
33 import org.eclipse.core.runtime.FileLocator;
34 import org.eclipse.core.runtime.IPath;
35 import org.eclipse.core.runtime.Path;
36 import org.eclipse.core.runtime.Platform;
37 import org.eclipse.jface.viewers.AbstractTreeViewer;
38 import org.eclipse.jface.viewers.ColumnLabelProvider;
39 import org.eclipse.jface.viewers.ISelection;
40 import org.eclipse.jface.viewers.ISelectionChangedListener;
41 import org.eclipse.jface.viewers.IStructuredSelection;
42 import org.eclipse.jface.viewers.ITreeContentProvider;
43 import org.eclipse.jface.viewers.SelectionChangedEvent;
44 import org.eclipse.jface.viewers.StructuredSelection;
45 import org.eclipse.jface.viewers.TreeViewer;
46 import org.eclipse.jface.viewers.Viewer;
47 import org.eclipse.jface.wizard.WizardPage;
48 import org.eclipse.osgi.util.NLS;
49 import org.eclipse.swt.SWT;
50 import org.eclipse.swt.browser.Browser;
51 import org.eclipse.swt.custom.SashForm;
52 import org.eclipse.swt.custom.ScrolledComposite;
53 import org.eclipse.swt.custom.StyleRange;
54 import org.eclipse.swt.custom.StyledText;
55 import org.eclipse.swt.events.ModifyEvent;
56 import org.eclipse.swt.events.ModifyListener;
57 import org.eclipse.swt.events.SelectionAdapter;
58 import org.eclipse.swt.events.SelectionEvent;
59 import org.eclipse.swt.events.SelectionListener;
60 import org.eclipse.swt.graphics.Color;
61 import org.eclipse.swt.graphics.Font;
62 import org.eclipse.swt.graphics.FontData;
63 import org.eclipse.swt.graphics.Image;
64 import org.eclipse.swt.graphics.Point;
65 import org.eclipse.swt.graphics.Rectangle;
66 import org.eclipse.swt.layout.FillLayout;
67 import org.eclipse.swt.layout.GridData;
68 import org.eclipse.swt.layout.GridLayout;
69 import org.eclipse.swt.widgets.Button;
70 import org.eclipse.swt.widgets.Combo;
71 import org.eclipse.swt.widgets.Composite;
72 import org.eclipse.swt.widgets.Display;
73 import org.eclipse.swt.widgets.Group;
74 import org.eclipse.swt.widgets.Label;
75 import org.eclipse.swt.widgets.Shell;
76 import org.eclipse.swt.widgets.Text;
77 import org.eclipse.tracecompass.internal.tmf.ui.Activator;
78 import org.eclipse.tracecompass.internal.tmf.ui.Messages;
79 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomTraceDefinition;
80 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomTraceDefinition.Tag;
81 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomXmlInputAttribute;
82 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomXmlInputElement;
83 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomXmlTrace;
84 import org.eclipse.tracecompass.tmf.core.parsers.custom.CustomXmlTraceDefinition;
85 import org.eclipse.tracecompass.tmf.core.project.model.TmfTraceType;
86 import org.eclipse.tracecompass.tmf.core.project.model.TraceTypeHelper;
87 import org.eclipse.tracecompass.tmf.core.timestamp.TmfTimestampFormat;
88 import org.osgi.framework.Bundle;
89 import org.w3c.dom.Document;
90 import org.w3c.dom.Element;
91 import org.w3c.dom.NamedNodeMap;
92 import org.w3c.dom.Node;
93 import org.w3c.dom.NodeList;
94 import org.xml.sax.EntityResolver;
95 import org.xml.sax.ErrorHandler;
96 import org.xml.sax.InputSource;
97 import org.xml.sax.SAXException;
98 import org.xml.sax.SAXParseException;
99
100 import com.google.common.base.Joiner;
101
102 /**
103 * Input wizard page for custom XML trace parsers.
104 *
105 * @author Patrick Tasse
106 */
107 public class CustomXmlParserInputWizardPage extends WizardPage {
108
109 private static final String DEFAULT_TIMESTAMP_FORMAT = "yyyy-MM-dd HH:mm:ss.SSS"; //$NON-NLS-1$
110 private static final String TIMESTAMP_FORMAT_BUNDLE = "org.eclipse.tracecompass.doc.user"; //$NON-NLS-1$
111 private static final String TIMESTAMP_FORMAT_PATH = "reference/api/org/eclipse/tracecompass/tmf/core/timestamp/TmfTimestampFormat.html"; //$NON-NLS-1$
112 private static final Image ELEMENT_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/element_icon.gif"); //$NON-NLS-1$
113 private static final Image ADD_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/add_button.gif"); //$NON-NLS-1$
114 private static final Image ADD_NEXT_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/addnext_button.gif"); //$NON-NLS-1$
115 private static final Image ADD_CHILD_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/addchild_button.gif"); //$NON-NLS-1$
116 private static final Image ADD_MANY_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/addmany_button.gif"); //$NON-NLS-1$
117 private static final Image DELETE_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/delete_button.gif"); //$NON-NLS-1$
118 private static final Image MOVE_UP_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/moveup_button.gif"); //$NON-NLS-1$
119 private static final Image MOVE_DOWN_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/movedown_button.gif"); //$NON-NLS-1$
120 private static final Image HELP_IMAGE = Activator.getDefault().getImageFromPath("/icons/elcl16/help_button.gif"); //$NON-NLS-1$
121 private static final Color COLOR_LIGHT_RED = new Color(Display.getDefault(), 255, 192, 192);
122 private static final Color COLOR_TEXT_BACKGROUND = Display.getDefault().getSystemColor(SWT.COLOR_WHITE);
123 private static final Color COLOR_WIDGET_BACKGROUND = Display.getDefault().getSystemColor(SWT.COLOR_WIDGET_BACKGROUND);
124
125 private final ISelection selection;
126 private CustomXmlTraceDefinition definition;
127 private String editCategoryName;
128 private String editDefinitionName;
129 private String defaultDescription;
130 private ElementNode selectedElement;
131 private Composite container;
132 private Text categoryText;
133 private Text logtypeText;
134 private Text timeStampOutputFormatText;
135 private Text timeStampPreviewText;
136 private Button removeButton;
137 private Button addChildButton;
138 private Button addNextButton;
139 private Button moveUpButton;
140 private Button moveDownButton;
141 private ScrolledComposite elementScrolledComposite;
142 private TreeViewer treeViewer;
143 private Composite elementContainer;
144 private Text errorText;
145 private StyledText inputText;
146 private Font fixedFont;
147 private UpdateListener updateListener;
148 private Browser helpBrowser;
149 private Element documentElement;
150
151 // variables used recursively through element traversal
152 private String timeStampValue;
153 private String timeStampFormat;
154 private boolean timeStampFound;
155 private int logEntriesCount;
156 private boolean logEntryFound;
157
158 /**
159 * Constructor
160 *
161 * @param selection
162 * Selection object
163 * @param definition
164 * Trace definition
165 */
166 protected CustomXmlParserInputWizardPage(ISelection selection, CustomXmlTraceDefinition definition) {
167 super("CustomXmlParserWizardPage"); //$NON-NLS-1$
168 if (definition == null) {
169 setTitle(Messages.CustomXmlParserInputWizardPage_titleNew);
170 defaultDescription = Messages.CustomXmlParserInputWizardPage_descriptionNew;
171 } else {
172 setTitle(Messages.CustomXmlParserInputWizardPage_titleEdit);
173 defaultDescription = Messages.CustomXmlParserInputWizardPage_descriptionEdit;
174 }
175 setDescription(defaultDescription);
176 this.selection = selection;
177 this.definition = definition;
178 if (definition != null) {
179 this.editCategoryName = definition.categoryName;
180 this.editDefinitionName = definition.definitionName;
181 }
182 }
183
184 @Override
185 public void createControl(Composite parent) {
186 container = new Composite(parent, SWT.NULL);
187 container.setLayout(new GridLayout());
188
189 updateListener = new UpdateListener();
190
191 Composite headerComposite = new Composite(container, SWT.FILL);
192 GridLayout headerLayout = new GridLayout(5, false);
193 headerLayout.marginHeight = 0;
194 headerLayout.marginWidth = 0;
195 headerComposite.setLayout(headerLayout);
196 headerComposite.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
197
198 Label categoryLabel = new Label(headerComposite, SWT.NULL);
199 categoryLabel.setText(Messages.CustomXmlParserInputWizardPage_category);
200
201 categoryText = new Text(headerComposite, SWT.BORDER | SWT.SINGLE);
202 categoryText.setLayoutData(new GridData(120, SWT.DEFAULT));
203
204 Label timeStampFormatLabel = new Label(headerComposite, SWT.NULL);
205 timeStampFormatLabel.setText(Messages.CustomXmlParserInputWizardPage_timestampFormat);
206
207 timeStampOutputFormatText = new Text(headerComposite, SWT.BORDER | SWT.SINGLE);
208 timeStampOutputFormatText.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
209 timeStampOutputFormatText.setText(DEFAULT_TIMESTAMP_FORMAT);
210
211 Button timeStampFormatHelpButton = new Button(headerComposite, SWT.PUSH);
212 timeStampFormatHelpButton.setImage(HELP_IMAGE);
213 timeStampFormatHelpButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_timestampFormatHelp);
214 timeStampFormatHelpButton.addSelectionListener(new SelectionAdapter() {
215 @Override
216 public void widgetSelected(SelectionEvent e) {
217 Bundle plugin = Platform.getBundle(TIMESTAMP_FORMAT_BUNDLE);
218 IPath path = new Path(TIMESTAMP_FORMAT_PATH);
219 URL fileURL = FileLocator.find(plugin, path, null);
220 try {
221 URL pageURL = FileLocator.toFileURL(fileURL);
222 openHelpShell(pageURL.toString());
223 } catch (IOException e1) {
224 }
225 }
226 });
227
228 Label logtypeLabel = new Label(headerComposite, SWT.NULL);
229 logtypeLabel.setText(Messages.CustomXmlParserInputWizardPage_logType);
230
231 logtypeText = new Text(headerComposite, SWT.BORDER | SWT.SINGLE);
232 logtypeText.setLayoutData(new GridData(120, SWT.DEFAULT));
233 logtypeText.setFocus();
234
235 Label timeStampPreviewLabel = new Label(headerComposite, SWT.NULL);
236 timeStampPreviewLabel.setText(Messages.CustomXmlParserInputWizardPage_preview);
237
238 timeStampPreviewText = new Text(headerComposite, SWT.BORDER | SWT.SINGLE | SWT.READ_ONLY);
239 timeStampPreviewText.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false, 2, 1));
240 timeStampPreviewText.setText("*no time stamp element or attribute*"); //$NON-NLS-1$
241
242 createButtonBar();
243
244 SashForm vSash = new SashForm(container, SWT.VERTICAL);
245 vSash.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
246 vSash.setBackground(vSash.getDisplay().getSystemColor(SWT.COLOR_GRAY));
247
248 SashForm hSash = new SashForm(vSash, SWT.HORIZONTAL);
249 hSash.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
250
251 ScrolledComposite treeScrolledComposite = new ScrolledComposite(hSash, SWT.V_SCROLL | SWT.H_SCROLL);
252 treeScrolledComposite.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
253 Composite treeContainer = new Composite(treeScrolledComposite, SWT.NONE);
254 treeContainer.setLayout(new FillLayout());
255 treeScrolledComposite.setContent(treeContainer);
256 treeScrolledComposite.setExpandHorizontal(true);
257 treeScrolledComposite.setExpandVertical(true);
258
259 treeViewer = new TreeViewer(treeContainer, SWT.SINGLE | SWT.BORDER);
260 treeViewer.setContentProvider(new InputElementTreeNodeContentProvider());
261 treeViewer.setLabelProvider(new InputElementTreeLabelProvider());
262 treeViewer.addSelectionChangedListener(new InputElementTreeSelectionChangedListener());
263 treeContainer.layout();
264
265 treeScrolledComposite
266 .setMinSize(treeContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x, treeContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y);
267
268 elementScrolledComposite = new ScrolledComposite(hSash, SWT.V_SCROLL);
269 elementScrolledComposite.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true));
270 elementContainer = new Composite(elementScrolledComposite, SWT.NONE);
271 GridLayout gl = new GridLayout();
272 gl.marginHeight = 1;
273 gl.marginWidth = 0;
274 elementContainer.setLayout(gl);
275 elementScrolledComposite.setContent(elementContainer);
276 elementScrolledComposite.setExpandHorizontal(true);
277 elementScrolledComposite.setExpandVertical(true);
278
279 if (definition == null) {
280 definition = new CustomXmlTraceDefinition();
281 }
282 loadDefinition(definition);
283 treeViewer.expandAll();
284 elementContainer.layout();
285
286 categoryText.addModifyListener(updateListener);
287 logtypeText.addModifyListener(updateListener);
288 timeStampOutputFormatText.addModifyListener(updateListener);
289
290 elementScrolledComposite.setMinSize(elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x,
291 elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y - 1);
292
293 hSash.setWeights(new int[] { 1, 2 });
294
295 if (definition.rootInputElement == null) {
296 removeButton.setEnabled(false);
297 addChildButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addDocumentElement);
298 addNextButton.setEnabled(false);
299 moveUpButton.setEnabled(false);
300 moveDownButton.setEnabled(false);
301 } else { // root is selected
302 addNextButton.setEnabled(false);
303 }
304
305 Composite sashBottom = new Composite(vSash, SWT.NONE);
306 GridLayout sashBottomLayout = new GridLayout(2, false);
307 sashBottomLayout.marginHeight = 0;
308 sashBottomLayout.marginWidth = 0;
309 sashBottom.setLayout(sashBottomLayout);
310
311 Label previewLabel = new Label(sashBottom, SWT.NULL);
312 previewLabel.setText(Messages.CustomXmlParserInputWizardPage_previewInput);
313
314 errorText = new Text(sashBottom, SWT.SINGLE | SWT.READ_ONLY);
315 errorText.setBackground(COLOR_WIDGET_BACKGROUND);
316 errorText.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
317 errorText.setVisible(false);
318
319 inputText = new StyledText(sashBottom, SWT.MULTI | SWT.V_SCROLL | SWT.H_SCROLL);
320 if (fixedFont == null) {
321 if (System.getProperty("os.name").contains("Windows")) { //$NON-NLS-1$ //$NON-NLS-2$
322 fixedFont = new Font(Display.getCurrent(), new FontData("Courier New", 10, SWT.NORMAL)); //$NON-NLS-1$
323 } else {
324 fixedFont = new Font(Display.getCurrent(), new FontData("Monospace", 10, SWT.NORMAL)); //$NON-NLS-1$
325 }
326 }
327 inputText.setFont(fixedFont);
328 GridData gd = new GridData(SWT.FILL, SWT.FILL, true, true, 2, 1);
329 gd.heightHint = inputText.computeSize(SWT.DEFAULT, inputText.getLineHeight() * 4).y;
330 gd.widthHint = 800;
331 inputText.setLayoutData(gd);
332 inputText.setText(getSelectionText());
333 inputText.addModifyListener(e -> parseXmlInput(inputText.getText()));
334 inputText.addModifyListener(updateListener);
335
336 vSash.setWeights(new int[] { hSash.computeSize(SWT.DEFAULT, SWT.DEFAULT).y, sashBottom.computeSize(SWT.DEFAULT, SWT.DEFAULT).y });
337
338 setControl(container);
339 }
340
341 private void createButtonBar() {
342 Composite buttonBar = new Composite(container, SWT.NONE);
343 GridLayout buttonBarLayout = new GridLayout(6, false);
344 buttonBarLayout.marginHeight = 0;
345 buttonBarLayout.marginWidth = 0;
346 buttonBar.setLayout(buttonBarLayout);
347
348 removeButton = new Button(buttonBar, SWT.PUSH);
349 removeButton.setImage(DELETE_IMAGE);
350 removeButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_removeElement);
351 removeButton.addSelectionListener(new SelectionAdapter() {
352 @Override
353 public void widgetSelected(SelectionEvent e) {
354 if (treeViewer.getSelection().isEmpty() || selectedElement == null) {
355 return;
356 }
357 removeElement();
358 CustomXmlInputElement inputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
359 if (inputElement == definition.rootInputElement) {
360 definition.rootInputElement = null;
361 } else {
362 inputElement.getParentElement().getChildElements().remove(inputElement);
363 }
364 treeViewer.refresh();
365 validate();
366 updatePreviews();
367 removeButton.setEnabled(false);
368 if (definition.rootInputElement == null) {
369 addChildButton.setEnabled(true);
370 addChildButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addDocumentEleemnt);
371 } else {
372 addChildButton.setEnabled(false);
373 }
374 addNextButton.setEnabled(false);
375 moveUpButton.setEnabled(false);
376 moveDownButton.setEnabled(false);
377 }
378 });
379
380 addChildButton = new Button(buttonBar, SWT.PUSH);
381 addChildButton.setImage(ADD_CHILD_IMAGE);
382 addChildButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addChildElement);
383 addChildButton.addSelectionListener(new SelectionAdapter() {
384 @Override
385 public void widgetSelected(SelectionEvent e) {
386 CustomXmlInputElement inputElement = new CustomXmlInputElement("", false, Tag.IGNORE, Tag.IGNORE.toString(), 0, "", null); //$NON-NLS-1$ //$NON-NLS-2$
387 if (definition.rootInputElement == null) {
388 definition.rootInputElement = inputElement;
389 inputElement.setElementName(getChildNameSuggestion(null));
390 } else if (treeViewer.getSelection().isEmpty()) {
391 return;
392 } else {
393 CustomXmlInputElement parentInputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
394 parentInputElement.addChild(inputElement);
395 inputElement.setElementName(getChildNameSuggestion(parentInputElement));
396 }
397 treeViewer.refresh();
398 treeViewer.setSelection(new StructuredSelection(inputElement), true);
399 }
400 });
401
402 addNextButton = new Button(buttonBar, SWT.PUSH);
403 addNextButton.setImage(ADD_NEXT_IMAGE);
404 addNextButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addNextElement);
405 addNextButton.addSelectionListener(new SelectionAdapter() {
406 @Override
407 public void widgetSelected(SelectionEvent e) {
408 CustomXmlInputElement inputElement = new CustomXmlInputElement("", false, Tag.IGNORE, Tag.IGNORE.toString(), 0, "", null); //$NON-NLS-1$ //$NON-NLS-2$
409 if (definition.rootInputElement == null) {
410 definition.rootInputElement = inputElement;
411 inputElement.setElementName(getChildNameSuggestion(null));
412 } else if (treeViewer.getSelection().isEmpty()) {
413 return;
414 } else {
415 CustomXmlInputElement previousInputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
416 if (previousInputElement == definition.rootInputElement) {
417 return;
418 }
419 previousInputElement.addNext(inputElement);
420 inputElement.setElementName(getChildNameSuggestion(inputElement.getParentElement()));
421 }
422 treeViewer.refresh();
423 treeViewer.setSelection(new StructuredSelection(inputElement), true);
424 }
425 });
426
427 Button feelingLuckyButton = new Button(buttonBar, SWT.PUSH);
428 feelingLuckyButton.setImage(ADD_MANY_IMAGE);
429 feelingLuckyButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_feelingLucky);
430 feelingLuckyButton.addSelectionListener(new SelectionAdapter() {
431 @Override
432 public void widgetSelected(SelectionEvent e) {
433 CustomXmlInputElement inputElement = null;
434 if (definition.rootInputElement == null) {
435 if (getChildNameSuggestion(null).length() != 0) {
436 inputElement = new CustomXmlInputElement(getChildNameSuggestion(null), false, Tag.IGNORE, Tag.IGNORE.toString(), 0, "", null); //$NON-NLS-1$
437 definition.rootInputElement = inputElement;
438 feelingLucky(inputElement);
439 } else {
440 return;
441 }
442 } else if (treeViewer.getSelection().isEmpty()) {
443 return;
444 } else {
445 inputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
446 feelingLucky(inputElement);
447 }
448 treeViewer.refresh();
449 treeViewer.setSelection(new StructuredSelection(inputElement), true);
450 treeViewer.expandToLevel(inputElement, AbstractTreeViewer.ALL_LEVELS);
451 }
452 });
453
454 moveUpButton = new Button(buttonBar, SWT.PUSH);
455 moveUpButton.setImage(MOVE_UP_IMAGE);
456 moveUpButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_moveUp);
457 moveUpButton.addSelectionListener(new SelectionAdapter() {
458 @Override
459 public void widgetSelected(SelectionEvent e) {
460 if (treeViewer.getSelection().isEmpty()) {
461 return;
462 }
463 CustomXmlInputElement inputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
464 if (inputElement == definition.rootInputElement) {
465 return;
466 }
467 inputElement.moveUp();
468 treeViewer.refresh();
469 validate();
470 updatePreviews();
471 }
472 });
473
474 moveDownButton = new Button(buttonBar, SWT.PUSH);
475 moveDownButton.setImage(MOVE_DOWN_IMAGE);
476 moveDownButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_moveDown);
477 moveDownButton.addSelectionListener(new SelectionAdapter() {
478 @Override
479 public void widgetSelected(SelectionEvent e) {
480 if (treeViewer.getSelection().isEmpty()) {
481 return;
482 }
483 CustomXmlInputElement inputElement = (CustomXmlInputElement) ((IStructuredSelection) treeViewer.getSelection()).getFirstElement();
484 if (inputElement == definition.rootInputElement) {
485 return;
486 }
487 inputElement.moveDown();
488 treeViewer.refresh();
489 validate();
490 updatePreviews();
491 }
492 });
493 }
494
495 private void feelingLucky(CustomXmlInputElement inputElement) {
496 while (true) {
497 String attributeName = getAttributeNameSuggestion(inputElement);
498 if (attributeName.length() == 0) {
499 break;
500 }
501 CustomXmlInputAttribute attribute = new CustomXmlInputAttribute(attributeName, Tag.OTHER, attributeName, 0, ""); //$NON-NLS-1$
502 inputElement.addAttribute(attribute);
503 }
504 while (true) {
505 String childName = getChildNameSuggestion(inputElement);
506 if (childName.length() == 0) {
507 break;
508 }
509 CustomXmlInputElement childElement = new CustomXmlInputElement(childName, false, Tag.IGNORE, Tag.IGNORE.toString(), 0, "", null); //$NON-NLS-1$
510 inputElement.addChild(childElement);
511 feelingLucky(childElement);
512 }
513 }
514
515 private static class InputElementTreeNodeContentProvider implements ITreeContentProvider {
516
517 @Override
518 public Object[] getElements(Object inputElement) {
519 CustomXmlTraceDefinition def = (CustomXmlTraceDefinition) inputElement;
520 if (def.rootInputElement != null) {
521 return new Object[] { def.rootInputElement };
522 }
523 return new Object[0];
524 }
525
526 @Override
527 public Object[] getChildren(Object parentElement) {
528 CustomXmlInputElement inputElement = (CustomXmlInputElement) parentElement;
529 if (inputElement.getChildElements() == null) {
530 return new CustomXmlInputElement[0];
531 }
532 return inputElement.getChildElements().toArray();
533 }
534
535 @Override
536 public boolean hasChildren(Object element) {
537 CustomXmlInputElement inputElement = (CustomXmlInputElement) element;
538 return (inputElement.getChildElements() != null && inputElement.getChildElements().size() > 0);
539 }
540
541 @Override
542 public void dispose() {
543 }
544
545 @Override
546 public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
547 }
548
549 @Override
550 public Object getParent(Object element) {
551 CustomXmlInputElement inputElement = (CustomXmlInputElement) element;
552 return inputElement.getParentElement();
553 }
554 }
555
556 private static class InputElementTreeLabelProvider extends ColumnLabelProvider {
557
558 @Override
559 public Image getImage(Object element) {
560 return ELEMENT_IMAGE;
561 }
562
563 @Override
564 public String getText(Object element) {
565 CustomXmlInputElement inputElement = (CustomXmlInputElement) element;
566 return (inputElement.getElementName().trim().length() == 0) ? "?" : inputElement.getElementName(); //$NON-NLS-1$
567 }
568 }
569
570 private class InputElementTreeSelectionChangedListener implements ISelectionChangedListener {
571 @Override
572 public void selectionChanged(SelectionChangedEvent event) {
573 if (selectedElement != null) {
574 selectedElement.dispose();
575 }
576 if (!(event.getSelection().isEmpty()) && event.getSelection() instanceof IStructuredSelection) {
577 IStructuredSelection sel = (IStructuredSelection) event.getSelection();
578 CustomXmlInputElement inputElement = (CustomXmlInputElement) sel.getFirstElement();
579 selectedElement = new ElementNode(elementContainer, inputElement);
580 elementContainer.layout();
581 elementScrolledComposite.setMinSize(elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x,
582 elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y - 1);
583 container.layout();
584 validate();
585 updatePreviews();
586 removeButton.setEnabled(true);
587 addChildButton.setEnabled(true);
588 addChildButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addChildElement);
589 if (definition.rootInputElement == inputElement) {
590 addNextButton.setEnabled(false);
591 } else {
592 addNextButton.setEnabled(true);
593 }
594 moveUpButton.setEnabled(true);
595 moveDownButton.setEnabled(true);
596 } else {
597 removeButton.setEnabled(false);
598 if (definition.rootInputElement == null) {
599 addChildButton.setEnabled(true);
600 addChildButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addDocumentElement);
601 } else {
602 addChildButton.setEnabled(false);
603 }
604 addNextButton.setEnabled(false);
605 moveUpButton.setEnabled(false);
606 moveDownButton.setEnabled(false);
607 }
608 }
609 }
610
611 @Override
612 public void dispose() {
613 if (fixedFont != null) {
614 fixedFont.dispose();
615 fixedFont = null;
616 }
617 super.dispose();
618 }
619
620 private void loadDefinition(CustomXmlTraceDefinition def) {
621 categoryText.setText(def.categoryName);
622 logtypeText.setText(def.definitionName);
623 timeStampOutputFormatText.setText(def.timeStampOutputFormat);
624 treeViewer.setInput(def);
625
626 if (def.rootInputElement != null) {
627 treeViewer.setSelection(new StructuredSelection(def.rootInputElement));
628 }
629 }
630
631 private String getName(CustomXmlInputElement inputElement) {
632 String name = (inputElement.getElementName().trim().length() == 0) ? "?" : inputElement.getElementName().trim(); //$NON-NLS-1$
633 if (inputElement.getParentElement() == null) {
634 return name;
635 }
636 return getName(inputElement.getParentElement()) + " : " + name; //$NON-NLS-1$
637 }
638
639 private String getName(CustomXmlInputAttribute inputAttribute, CustomXmlInputElement inputElement) {
640 String name = (inputAttribute.getAttributeName().trim().length() == 0) ? "?" : inputAttribute.getAttributeName().trim(); //$NON-NLS-1$
641 return getName(inputElement) + " : " + name; //$NON-NLS-1$
642 }
643
644 @Override
645 public void setVisible(boolean visible) {
646 if (visible) {
647 validate();
648 updatePreviews();
649 }
650 super.setVisible(visible);
651 }
652
653 /**
654 * Get the global list of inputs.
655 *
656 * @return The list of inputs
657 */
658 public List<Entry<Tag, String>> getInputs() {
659 return getInputs(definition.rootInputElement);
660 }
661
662 /**
663 * Get the list of inputs for a given element, recursively.
664 *
665 * @param inputElement
666 * The element
667 * @return The list of inputs
668 */
669 public List<Entry<Tag, String>> getInputs(CustomXmlInputElement inputElement) {
670 List<Entry<Tag, String>> inputs = new ArrayList<>();
671 if (inputElement.getInputTag() != null && !inputElement.getInputTag().equals(Tag.IGNORE)) {
672 Entry<Tag, String> input = new SimpleEntry<>(inputElement.getInputTag(), inputElement.getInputName());
673 if (!inputs.contains(input)) {
674 inputs.add(input);
675 }
676 }
677 if (inputElement.getAttributes() != null) {
678 for (CustomXmlInputAttribute attribute : inputElement.getAttributes()) {
679 Entry<Tag, String> input = new SimpleEntry<>(attribute.getInputTag(), attribute.getInputName());
680 if (!inputs.contains(input)) {
681 inputs.add(input);
682 }
683 }
684 }
685 if (inputElement.getChildElements() != null) {
686 for (CustomXmlInputElement childInputElement : inputElement.getChildElements()) {
687 for (Entry<Tag, String> input : getInputs(childInputElement)) {
688 if (!inputs.contains(input)) {
689 inputs.add(input);
690 }
691 }
692 }
693 }
694 return inputs;
695 }
696
697 private void removeElement() {
698 selectedElement.dispose();
699 selectedElement = null;
700 elementContainer.layout();
701 elementScrolledComposite.setMinSize(elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x,
702 elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y - 1);
703 container.layout();
704 }
705
706 private String getSelectionText() {
707 InputStream inputStream = null;
708 if (this.selection instanceof IStructuredSelection) {
709 Object sel = ((IStructuredSelection) this.selection).getFirstElement();
710 if (sel instanceof IFile) {
711 IFile file = (IFile) sel;
712 try {
713 inputStream = file.getContents();
714 } catch (CoreException e) {
715 return ""; //$NON-NLS-1$
716 }
717 }
718 }
719 if (inputStream != null) {
720 try (BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream));) {
721 StringBuilder sb = new StringBuilder();
722 String line = null;
723 while ((line = reader.readLine()) != null) {
724 sb.append(line);
725 sb.append('\n');
726 }
727 parseXmlInput(sb.toString());
728 return sb.toString();
729 } catch (IOException e) {
730 return ""; //$NON-NLS-1$
731 }
732 }
733 return ""; //$NON-NLS-1$
734 }
735
736 private void parseXmlInput(final String string) {
737 try {
738 DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
739 DocumentBuilder db = dbf.newDocumentBuilder();
740
741 // The following allows xml parsing without access to the dtd
742 EntityResolver resolver = (publicId, systemId) -> {
743 String empty = ""; //$NON-NLS-1$
744 ByteArrayInputStream bais = new ByteArrayInputStream(empty.getBytes());
745 return new InputSource(bais);
746 };
747 db.setEntityResolver(resolver);
748
749 // The following catches xml parsing exceptions
750 db.setErrorHandler(new ErrorHandler() {
751 @Override
752 public void error(SAXParseException saxparseexception) throws SAXException {
753 }
754
755 @Override
756 public void warning(SAXParseException saxparseexception) throws SAXException {
757 }
758
759 @Override
760 public void fatalError(SAXParseException saxparseexception) throws SAXException {
761 if (string.trim().length() != 0) {
762 errorText.setText(saxparseexception.getMessage());
763 errorText.setBackground(COLOR_LIGHT_RED);
764 errorText.setVisible(true);
765 }
766 throw saxparseexception;
767 }
768 });
769
770 errorText.setVisible(false);
771 Document doc = null;
772 doc = db.parse(new ByteArrayInputStream(string.getBytes()));
773 documentElement = doc.getDocumentElement();
774 } catch (ParserConfigurationException e) {
775 Activator.getDefault().logError("Error pasing XML input string: " + string, e); //$NON-NLS-1$
776 documentElement = null;
777 } catch (SAXException e) {
778 documentElement = null;
779 } catch (IOException e) {
780 Activator.getDefault().logError("Error pasing XML input string: " + string, e); //$NON-NLS-1$
781 documentElement = null;
782 }
783 }
784
785 private void initValues() {
786 timeStampValue = null;
787 timeStampFormat = null;
788 logEntriesCount = 0;
789 logEntryFound = false;
790 }
791
792 private void updatePreviews() {
793 if (inputText == null) {
794 // early update during construction
795 return;
796 }
797 inputText.setStyleRanges(new StyleRange[] {});
798 if (selectedElement == null) {
799 return;
800 }
801
802 initValues();
803
804 selectedElement.updatePreview();
805
806 if (timeStampValue != null && timeStampFormat != null) {
807 try {
808 TmfTimestampFormat timestampFormat = new TmfTimestampFormat(timeStampFormat);
809 long timestamp = timestampFormat.parseValue(timeStampValue);
810 timestampFormat = new TmfTimestampFormat(timeStampOutputFormatText.getText().trim());
811 timeStampPreviewText.setText(timestampFormat.format(timestamp));
812 } catch (ParseException e) {
813 timeStampPreviewText.setText("*parse exception* [" + timeStampValue + "] <> [" + timeStampFormat + "]"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
814 } catch (IllegalArgumentException e) {
815 timeStampPreviewText.setText("*parse exception* [Illegal Argument]"); //$NON-NLS-1$
816 }
817 } else {
818 timeStampPreviewText.setText("*no matching time stamp*"); //$NON-NLS-1$
819 }
820 }
821
822 private void openHelpShell(String url) {
823 if (helpBrowser != null && !helpBrowser.isDisposed()) {
824 helpBrowser.getShell().setActive();
825 if (!helpBrowser.getUrl().equals(url)) {
826 helpBrowser.setUrl(url);
827 }
828 return;
829 }
830 final Shell helpShell = new Shell(getShell(), SWT.SHELL_TRIM);
831 helpShell.setLayout(new FillLayout());
832 helpBrowser = new Browser(helpShell, SWT.NONE);
833 helpBrowser.addTitleListener(event -> helpShell.setText(event.title));
834 Rectangle r = container.getBounds();
835 Point p = container.toDisplay(r.x, r.y);
836 Rectangle trim = helpShell.computeTrim(p.x + (r.width - 750) / 2, p.y + (r.height - 400) / 2, 750, 400);
837 helpShell.setBounds(trim);
838 helpShell.open();
839 helpBrowser.setUrl(url);
840 }
841
842 private class UpdateListener implements ModifyListener, SelectionListener {
843
844 @Override
845 public void modifyText(ModifyEvent e) {
846 validate();
847 updatePreviews();
848 }
849
850 @Override
851 public void widgetDefaultSelected(SelectionEvent e) {
852 validate();
853 updatePreviews();
854 }
855
856 @Override
857 public void widgetSelected(SelectionEvent e) {
858 validate();
859 updatePreviews();
860 }
861
862 }
863
864 private class ElementNode {
865 private final CustomXmlInputElement inputElement;
866 private final Group group;
867 private List<Attribute> attributes = new ArrayList<>();
868 private List<ElementNode> childElements = new ArrayList<>();
869 private Text elementNameText;
870 private Composite tagComposite;
871 private Combo tagCombo;
872 private Label tagLabel;
873 private Text tagText;
874 private Combo actionCombo;
875 private Label previewLabel;
876 private Text previewText;
877 private Button logEntryButton;
878 private Button eventTypeButton;
879 private Text eventTypeText;
880 private Label fillerLabel;
881 private Composite addAttributeComposite;
882 private Button addAttributeButton;
883 private Label addAttributeLabel;
884
885 public ElementNode(Composite parent, CustomXmlInputElement inputElement) {
886 this.inputElement = inputElement;
887
888 group = new Group(parent, SWT.NONE);
889 GridLayout gl = new GridLayout(2, false);
890 gl.marginHeight = 0;
891 group.setLayout(gl);
892 group.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
893 group.setText(getName(inputElement));
894
895 Label label = new Label(group, SWT.NULL);
896 label.setText(Messages.CustomXmlParserInputWizardPage_elementName);
897 label.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
898
899 elementNameText = new Text(group, SWT.BORDER | SWT.SINGLE);
900 GridData gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
901 gd.widthHint = 0;
902 elementNameText.setLayoutData(gd);
903 elementNameText.addModifyListener(e -> {
904 ElementNode.this.inputElement.setElementName(elementNameText.getText().trim());
905 group.setText(getName(ElementNode.this.inputElement));
906 });
907 elementNameText.setText(inputElement.getElementName());
908 elementNameText.addModifyListener(updateListener);
909
910 if (inputElement.getParentElement() != null) {
911 previewLabel = new Label(group, SWT.NULL);
912 previewLabel.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
913 previewLabel.setText(Messages.CustomXmlParserInputWizardPage_preview);
914
915 previewText = new Text(group, SWT.BORDER | SWT.SINGLE | SWT.READ_ONLY);
916 gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
917 gd.widthHint = 0;
918 previewText.setLayoutData(gd);
919 previewText.setText(Messages.CustomXmlParserInputWizardPage_noMatchingElement);
920 previewText.setBackground(COLOR_WIDGET_BACKGROUND);
921
922 logEntryButton = new Button(group, SWT.CHECK);
923 logEntryButton.setText(Messages.CustomXmlParserInputWizardPage_logEntry);
924 logEntryButton.setSelection(inputElement.isLogEntry());
925 logEntryButton.addSelectionListener(new SelectionListener() {
926 @Override
927 public void widgetDefaultSelected(SelectionEvent e) {
928 }
929
930 @Override
931 public void widgetSelected(SelectionEvent e) {
932 CustomXmlInputElement parentElem = ElementNode.this.inputElement.getParentElement();
933 while (parentElem != null) {
934 parentElem.setLogEntry(false);
935 parentElem = parentElem.getParentElement();
936 }
937 }
938 });
939 logEntryButton.addSelectionListener(updateListener);
940
941 tagComposite = new Composite(group, SWT.FILL);
942 GridLayout tagLayout = new GridLayout(4, false);
943 tagLayout.marginWidth = 0;
944 tagLayout.marginHeight = 0;
945 tagComposite.setLayout(tagLayout);
946 tagComposite.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
947
948 tagCombo = new Combo(tagComposite, SWT.DROP_DOWN | SWT.READ_ONLY);
949 tagCombo.setItems(new String[] {
950 Tag.IGNORE.toString(),
951 Tag.TIMESTAMP.toString(),
952 Tag.EVENT_TYPE.toString(),
953 Tag.MESSAGE.toString(),
954 Tag.OTHER.toString() });
955 tagCombo.setVisibleItemCount(tagCombo.getItemCount());
956 tagCombo.addSelectionListener(new SelectionListener() {
957 @Override
958 public void widgetDefaultSelected(SelectionEvent e) {
959 }
960
961 @Override
962 public void widgetSelected(SelectionEvent e) {
963 tagText.removeModifyListener(updateListener);
964 switch (tagCombo.getSelectionIndex()) {
965 case 0: // Ignore
966 tagLabel.setVisible(false);
967 tagText.setVisible(false);
968 actionCombo.setVisible(false);
969 break;
970 case 1: // Time Stamp
971 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_format);
972 tagLabel.setVisible(true);
973 tagText.setVisible(true);
974 tagText.addModifyListener(updateListener);
975 actionCombo.setVisible(true);
976 break;
977 case 2: // Event type
978 tagLabel.setVisible(false);
979 tagText.setVisible(false);
980 actionCombo.setVisible(true);
981 break;
982 case 3: // Message
983 tagLabel.setVisible(false);
984 tagText.setVisible(false);
985 actionCombo.setVisible(true);
986 break;
987 case 4: // Other
988 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_name);
989 tagLabel.setVisible(true);
990 if (tagText.getText().trim().length() == 0) {
991 tagText.setText(elementNameText.getText().trim());
992 }
993 tagText.setVisible(true);
994 tagText.addModifyListener(updateListener);
995 actionCombo.setVisible(true);
996 break;
997 default:
998 break;
999 }
1000 tagComposite.layout();
1001 validate();
1002 updatePreviews();
1003 }
1004 });
1005
1006 tagLabel = new Label(tagComposite, SWT.NULL);
1007 tagLabel.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1008
1009 tagText = new Text(tagComposite, SWT.BORDER | SWT.SINGLE);
1010 gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
1011 gd.widthHint = 0;
1012 tagText.setLayoutData(gd);
1013
1014 actionCombo = new Combo(tagComposite, SWT.DROP_DOWN | SWT.READ_ONLY);
1015 actionCombo.setItems(new String[] { Messages.CustomXmlParserInputWizardPage_set, Messages.CustomXmlParserInputWizardPage_append,
1016 Messages.CustomXmlParserInputWizardPage_appendWith });
1017 actionCombo.select(inputElement.getInputAction());
1018 actionCombo.addSelectionListener(updateListener);
1019
1020 if (inputElement.getInputTag().equals(Tag.IGNORE)) {
1021 tagCombo.select(0);
1022 tagLabel.setVisible(false);
1023 tagText.setVisible(false);
1024 actionCombo.setVisible(false);
1025 } else if (inputElement.getInputTag().equals(Tag.TIMESTAMP)) {
1026 tagCombo.select(1);
1027 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_format);
1028 tagText.setText(inputElement.getInputFormat());
1029 tagText.addModifyListener(updateListener);
1030 } else if (inputElement.getInputTag().equals(Tag.EVENT_TYPE)) {
1031 tagCombo.select(2);
1032 tagLabel.setVisible(false);
1033 tagText.setVisible(false);
1034 } else if (inputElement.getInputTag().equals(Tag.MESSAGE)) {
1035 tagCombo.select(3);
1036 tagLabel.setVisible(false);
1037 tagText.setVisible(false);
1038 } else {
1039 tagCombo.select(4);
1040 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_name);
1041 tagText.setText(inputElement.getInputName());
1042 tagText.addModifyListener(updateListener);
1043 }
1044
1045 eventTypeButton = new Button(group, SWT.CHECK);
1046 eventTypeButton.setText(Messages.CustomTxtParserInputWizardPage_eventType);
1047 eventTypeButton.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1048 eventTypeButton.addSelectionListener(new SelectionAdapter() {
1049 @Override
1050 public void widgetSelected(SelectionEvent e) {
1051 if (eventTypeButton.getSelection()) {
1052 eventTypeText.setEnabled(true);
1053 } else {
1054 eventTypeText.setEnabled(false);
1055 }
1056 }
1057 });
1058 eventTypeButton.addSelectionListener(updateListener);
1059
1060 eventTypeText = new Text(group, SWT.BORDER | SWT.SINGLE);
1061 gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
1062 gd.widthHint = 0;
1063 eventTypeText.setLayoutData(gd);
1064 if (inputElement.getEventType() != null) {
1065 eventTypeText.setText(inputElement.getEventType());
1066 eventTypeButton.setSelection(true);
1067 } else {
1068 eventTypeText.setEnabled(false);
1069 eventTypeButton.setSelection(false);
1070 }
1071 eventTypeText.addModifyListener(updateListener);
1072 }
1073
1074 if (inputElement.getAttributes() != null) {
1075 for (CustomXmlInputAttribute inputAttribute : inputElement.getAttributes()) {
1076 Attribute attribute = new Attribute(group, this, inputAttribute, attributes.size() + 1);
1077 attributes.add(attribute);
1078 }
1079 }
1080
1081 createAddButton();
1082 }
1083
1084 private void updatePreview() {
1085 Element element = getPreviewElement(inputElement);
1086 // no preview text for document element
1087 if (inputElement.getParentElement() != null) {
1088 previewText.setText(Messages.CustomXmlParserInputWizardPage_noMatchingElement);
1089 if (element != null) {
1090 previewText.setText(CustomXmlTrace.parseElement(element, new StringBuffer()).toString());
1091 if (logEntryButton.getSelection()) {
1092 if (!logEntryFound) {
1093 logEntryFound = true;
1094 logEntriesCount++;
1095 } else {
1096 // remove nested log entry
1097 logEntryButton.setSelection(false);
1098 }
1099 }
1100 if (tagCombo.getText().equals(Tag.TIMESTAMP.toString()) && logEntriesCount <= 1) {
1101 String value = previewText.getText().trim();
1102 if (value.length() != 0) {
1103 if (actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_SET) {
1104 timeStampValue = value;
1105 timeStampFormat = tagText.getText().trim();
1106 } else if (actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_APPEND) {
1107 if (timeStampValue != null) {
1108 timeStampValue += value;
1109 timeStampFormat += tagText.getText().trim();
1110 } else {
1111 timeStampValue = value;
1112 timeStampFormat = tagText.getText().trim();
1113 }
1114 } else if (actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_APPEND_WITH_SEPARATOR) {
1115 if (timeStampValue != null) {
1116 timeStampValue += " | " + value; //$NON-NLS-1$
1117 timeStampFormat += " | " + tagText.getText().trim(); //$NON-NLS-1$
1118 } else {
1119 timeStampValue = value;
1120 timeStampFormat = tagText.getText().trim();
1121 }
1122 }
1123 }
1124 }
1125 }
1126 }
1127 for (Attribute attribute : attributes) {
1128 if (element != null) {
1129 String value = element.getAttribute(attribute.attributeNameText.getText().trim());
1130 if (value.length() != 0) {
1131 attribute.previewText.setText(value);
1132 if (attribute.tagCombo.getText().equals(Tag.TIMESTAMP.toString()) && logEntriesCount <= 1) {
1133 if (attribute.actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_SET) {
1134 timeStampValue = value;
1135 timeStampFormat = attribute.tagText.getText().trim();
1136 } else if (attribute.actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_APPEND) {
1137 if (timeStampValue != null) {
1138 timeStampValue += value;
1139 timeStampFormat += attribute.tagText.getText().trim();
1140 } else {
1141 timeStampValue = value;
1142 timeStampFormat = attribute.tagText.getText().trim();
1143 }
1144 } else if (attribute.actionCombo.getSelectionIndex() == CustomTraceDefinition.ACTION_APPEND_WITH_SEPARATOR) {
1145 if (timeStampValue != null) {
1146 timeStampValue += " | " + value; //$NON-NLS-1$
1147 timeStampFormat += " | " + attribute.tagText.getText().trim(); //$NON-NLS-1$
1148 } else {
1149 timeStampValue = value;
1150 timeStampFormat = attribute.tagText.getText().trim();
1151 }
1152 }
1153 }
1154 } else {
1155 attribute.previewText.setText(Messages.CustomXmlParserInputWizardPage_noMatchingAttribute);
1156 }
1157 } else {
1158 attribute.previewText.setText(Messages.CustomXmlParserInputWizardPage_noMatchingElement);
1159 }
1160 }
1161 for (ElementNode child : childElements) {
1162 child.updatePreview();
1163 }
1164 if (logEntryButton != null && logEntryButton.getSelection()) {
1165 logEntryFound = false;
1166 }
1167 }
1168
1169 private void createAddButton() {
1170 fillerLabel = new Label(group, SWT.NONE);
1171
1172 addAttributeComposite = new Composite(group, SWT.NONE);
1173 addAttributeComposite.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
1174 GridLayout addAttributeLayout = new GridLayout(2, false);
1175 addAttributeLayout.marginHeight = 0;
1176 addAttributeLayout.marginWidth = 0;
1177 addAttributeComposite.setLayout(addAttributeLayout);
1178
1179 addAttributeButton = new Button(addAttributeComposite, SWT.PUSH);
1180 addAttributeButton.setImage(ADD_IMAGE);
1181 addAttributeButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_addAttribute);
1182 addAttributeButton.addSelectionListener(new SelectionAdapter() {
1183 @Override
1184 public void widgetSelected(SelectionEvent e) {
1185 removeAddButton();
1186 String attributeName = getAttributeNameSuggestion(inputElement);
1187 CustomXmlInputAttribute inputAttribute = new CustomXmlInputAttribute(attributeName, Tag.OTHER, attributeName, 0, ""); //$NON-NLS-1$
1188 attributes.add(new Attribute(group, ElementNode.this, inputAttribute, attributes.size() + 1));
1189 createAddButton();
1190 elementContainer.layout();
1191 elementScrolledComposite.setMinSize(elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x,
1192 elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y - 1);
1193 group.getParent().layout();
1194 validate();
1195 updatePreviews();
1196 }
1197 });
1198
1199 addAttributeLabel = new Label(addAttributeComposite, SWT.NULL);
1200 addAttributeLabel.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
1201 addAttributeLabel.setText(Messages.CustomXmlParserInputWizardPage_newAttibute);
1202 }
1203
1204 private void removeAddButton() {
1205 fillerLabel.dispose();
1206 addAttributeComposite.dispose();
1207 }
1208
1209 private void removeAttribute(int attributeNumber) {
1210 int nb = attributeNumber;
1211 if (--nb < attributes.size()) {
1212 attributes.remove(nb).dispose();
1213 for (int i = nb; i < attributes.size(); i++) {
1214 attributes.get(i).setAttributeNumber(i + 1);
1215 }
1216 elementContainer.layout();
1217 elementScrolledComposite.setMinSize(elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).x,
1218 elementContainer.computeSize(SWT.DEFAULT, SWT.DEFAULT).y - 1);
1219 group.getParent().layout();
1220 }
1221 }
1222
1223 private void dispose() {
1224 group.dispose();
1225 }
1226
1227 private void extractInputs() {
1228 inputElement.setElementName(elementNameText.getText().trim());
1229 if (inputElement.getParentElement() != null) {
1230 inputElement.setLogEntry(logEntryButton.getSelection());
1231 inputElement.setEventType(eventTypeButton.getSelection() ? eventTypeText.getText().trim() : null);
1232 Tag inputTag = Tag.fromLabel(tagCombo.getText());
1233 inputElement.setInputTag(inputTag);
1234 if (inputTag.equals(Tag.OTHER)) {
1235 inputElement.setInputName(tagText.getText().trim());
1236 } else {
1237 inputElement.setInputName(inputTag.toString());
1238 if (inputTag.equals(Tag.TIMESTAMP)) {
1239 inputElement.setInputFormat(tagText.getText().trim());
1240 }
1241 }
1242 inputElement.setInputAction(actionCombo.getSelectionIndex());
1243 }
1244 inputElement.setAttributes(new ArrayList<CustomXmlInputAttribute>(attributes.size()));
1245 for (int i = 0; i < attributes.size(); i++) {
1246 String inputName = null;
1247 String inputFormat = null;
1248 Attribute attribute = attributes.get(i);
1249 String attributeName = attribute.attributeNameText.getText().trim();
1250 Tag inputTag = Tag.fromLabel(attribute.tagCombo.getText());
1251 if (inputTag.equals(Tag.OTHER)) {
1252 inputName = attribute.tagText.getText().trim();
1253 } else {
1254 inputName = inputTag.toString();
1255 if (inputTag.equals(Tag.TIMESTAMP)) {
1256 inputFormat = attribute.tagText.getText().trim();
1257 }
1258 }
1259 int inputAction = attribute.actionCombo.getSelectionIndex();
1260 inputElement.addAttribute(new CustomXmlInputAttribute(attributeName, inputTag, inputName, inputAction, inputFormat));
1261 }
1262 }
1263 }
1264
1265 private class Attribute {
1266 private ElementNode element;
1267 private int attributeNumber;
1268
1269 // children of parent (must be disposed)
1270 private Composite labelComposite;
1271 private Composite attributeComposite;
1272 private Label filler;
1273 private Composite tagComposite;
1274
1275 // children of labelComposite
1276 private Label attributeLabel;
1277
1278 // children of attributeComposite
1279 private Text attributeNameText;
1280 private Text previewText;
1281
1282 // children of tagComposite
1283 private Combo tagCombo;
1284 private Label tagLabel;
1285 private Text tagText;
1286 private Combo actionCombo;
1287
1288 public Attribute(Composite parent, ElementNode element, CustomXmlInputAttribute inputAttribute, int attributeNumber) {
1289 this.element = element;
1290 this.attributeNumber = attributeNumber;
1291
1292 labelComposite = new Composite(parent, SWT.FILL);
1293 GridLayout labelLayout = new GridLayout(2, false);
1294 labelLayout.marginWidth = 0;
1295 labelLayout.marginHeight = 0;
1296 labelComposite.setLayout(labelLayout);
1297 labelComposite.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1298
1299 Button deleteButton = new Button(labelComposite, SWT.PUSH);
1300 deleteButton.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1301 deleteButton.setImage(DELETE_IMAGE);
1302 deleteButton.setToolTipText(Messages.CustomXmlParserInputWizardPage_removeAttribute);
1303 deleteButton.addSelectionListener(new SelectionAdapter() {
1304 @Override
1305 public void widgetSelected(SelectionEvent e) {
1306 Attribute.this.element.removeAttribute(Attribute.this.attributeNumber);
1307 validate();
1308 updatePreviews();
1309 }
1310 });
1311
1312 attributeLabel = new Label(labelComposite, SWT.NULL);
1313 attributeLabel.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1314 attributeLabel.setText(Messages.CustomXmlParserInputWizardPage_attibute);
1315
1316 attributeComposite = new Composite(parent, SWT.FILL);
1317 GridLayout attributeLayout = new GridLayout(4, false);
1318 attributeLayout.marginWidth = 0;
1319 attributeLayout.marginHeight = 0;
1320 attributeComposite.setLayout(attributeLayout);
1321 attributeComposite.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
1322
1323 Label nameLabel = new Label(attributeComposite, SWT.NONE);
1324 nameLabel.setText(Messages.CustomXmlParserInputWizardPage_name);
1325
1326 attributeNameText = new Text(attributeComposite, SWT.BORDER | SWT.SINGLE);
1327 attributeNameText.setLayoutData(new GridData(120, SWT.DEFAULT));
1328 attributeNameText.setText(inputAttribute.getAttributeName());
1329 attributeNameText.addModifyListener(updateListener);
1330
1331 Label previewLabel = new Label(attributeComposite, SWT.NONE);
1332 previewLabel.setText(Messages.CustomXmlParserInputWizardPage_preview);
1333
1334 previewText = new Text(attributeComposite, SWT.BORDER | SWT.SINGLE | SWT.READ_ONLY);
1335 GridData gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
1336 gd.widthHint = 0;
1337 previewText.setLayoutData(gd);
1338 previewText.setText(Messages.CustomXmlParserInputWizardPage_noMatch);
1339 previewText.setBackground(COLOR_WIDGET_BACKGROUND);
1340
1341 filler = new Label(parent, SWT.NULL);
1342
1343 tagComposite = new Composite(parent, SWT.FILL);
1344 GridLayout tagLayout = new GridLayout(4, false);
1345 tagLayout.marginWidth = 0;
1346 tagLayout.marginHeight = 0;
1347 tagComposite.setLayout(tagLayout);
1348 tagComposite.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
1349
1350 tagCombo = new Combo(tagComposite, SWT.DROP_DOWN | SWT.READ_ONLY);
1351 tagCombo.setItems(new String[] {
1352 Tag.TIMESTAMP.toString(),
1353 Tag.EVENT_TYPE.toString(),
1354 Tag.MESSAGE.toString(),
1355 Tag.OTHER.toString() });
1356 tagCombo.select(3); // Other
1357 tagCombo.addSelectionListener(new SelectionListener() {
1358 @Override
1359 public void widgetDefaultSelected(SelectionEvent e) {
1360 }
1361
1362 @Override
1363 public void widgetSelected(SelectionEvent e) {
1364 tagText.removeModifyListener(updateListener);
1365 switch (tagCombo.getSelectionIndex()) {
1366 case 0: // Time Stamp
1367 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_format);
1368 tagLabel.setVisible(true);
1369 tagText.setVisible(true);
1370 tagText.addModifyListener(updateListener);
1371 break;
1372 case 1: // Event type
1373 tagLabel.setVisible(false);
1374 tagText.setVisible(false);
1375 break;
1376 case 2: // Message
1377 tagLabel.setVisible(false);
1378 tagText.setVisible(false);
1379 break;
1380 case 3: // Other
1381 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_name);
1382 tagLabel.setVisible(true);
1383 if (tagText.getText().trim().length() == 0) {
1384 tagText.setText(attributeNameText.getText().trim());
1385 }
1386 tagText.setVisible(true);
1387 tagText.addModifyListener(updateListener);
1388 break;
1389 default:
1390 break;
1391 }
1392 tagComposite.layout();
1393 validate();
1394 updatePreviews();
1395 }
1396 });
1397
1398 tagLabel = new Label(tagComposite, SWT.NULL);
1399 tagLabel.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false));
1400
1401 tagText = new Text(tagComposite, SWT.BORDER | SWT.SINGLE);
1402 gd = new GridData(SWT.FILL, SWT.CENTER, true, false);
1403 gd.widthHint = 0;
1404 tagText.setLayoutData(gd);
1405 tagText.setText(attributeNameText.getText());
1406
1407 actionCombo = new Combo(tagComposite, SWT.DROP_DOWN | SWT.READ_ONLY);
1408 actionCombo.setItems(new String[] { Messages.CustomXmlParserInputWizardPage_set, Messages.CustomXmlParserInputWizardPage_append,
1409 Messages.CustomXmlParserInputWizardPage_appendWith });
1410 actionCombo.select(inputAttribute.getInputAction());
1411 actionCombo.addSelectionListener(updateListener);
1412
1413 if (inputAttribute.getInputTag().equals(Tag.TIMESTAMP)) {
1414 tagCombo.select(0);
1415 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_format);
1416 tagText.setText(inputAttribute.getInputFormat());
1417 tagText.addModifyListener(updateListener);
1418 } else if (inputAttribute.getInputTag().equals(Tag.EVENT_TYPE)) {
1419 tagCombo.select(1);
1420 tagLabel.setVisible(false);
1421 tagText.setVisible(false);
1422 } else if (inputAttribute.getInputTag().equals(Tag.MESSAGE)) {
1423 tagCombo.select(2);
1424 tagLabel.setVisible(false);
1425 tagText.setVisible(false);
1426 } else {
1427 tagCombo.select(3);
1428 tagLabel.setText(Messages.CustomXmlParserInputWizardPage_name);
1429 tagText.setText(inputAttribute.getInputName());
1430 tagText.addModifyListener(updateListener);
1431 }
1432 }
1433
1434 private void dispose() {
1435 labelComposite.dispose();
1436 attributeComposite.dispose();
1437 filler.dispose();
1438 tagComposite.dispose();
1439 }
1440
1441 private void setAttributeNumber(int attributeNumber) {
1442 this.attributeNumber = attributeNumber;
1443 labelComposite.layout();
1444 }
1445 }
1446
1447 private Element getPreviewElement(CustomXmlInputElement inputElement) {
1448 CustomXmlInputElement currentElement = inputElement;
1449 Element element = documentElement;
1450 if (element != null) {
1451 if (!documentElement.getNodeName().equals(definition.rootInputElement.getElementName())) {
1452 return null;
1453 }
1454 ArrayList<String> elementNames = new ArrayList<>();
1455 while (currentElement != null) {
1456 elementNames.add(currentElement.getElementName());
1457 currentElement = currentElement.getParentElement();
1458 }
1459 for (int i = elementNames.size() - 1; --i >= 0;) {
1460 NodeList childList = element.getChildNodes();
1461 element = null;
1462 for (int j = 0; j < childList.getLength(); j++) {
1463 Node child = childList.item(j);
1464 if (child instanceof Element && child.getNodeName().equals(elementNames.get(i))) {
1465 element = (Element) child;
1466 break;
1467 }
1468 }
1469 if (element == null) {
1470 break;
1471 }
1472 }
1473 if (element != null) {
1474 return element;
1475 }
1476 }
1477 return null;
1478 }
1479
1480 private String getChildNameSuggestion(CustomXmlInputElement inputElement) {
1481 if (inputElement == null) {
1482 if (documentElement != null) {
1483 return documentElement.getNodeName();
1484 }
1485 } else {
1486 Element element = getPreviewElement(inputElement);
1487 if (element != null) {
1488 NodeList childNodes = element.getChildNodes();
1489 for (int i = 0; i < childNodes.getLength(); i++) {
1490 Node node = childNodes.item(i);
1491 if (node instanceof Element) {
1492 boolean unused = true;
1493 if (inputElement.getChildElements() != null) {
1494 for (CustomXmlInputElement child : inputElement.getChildElements()) {
1495 if (child.getElementName().equals(node.getNodeName())) {
1496 unused = false;
1497 break;
1498 }
1499 }
1500 }
1501 if (unused) {
1502 return node.getNodeName();
1503 }
1504 }
1505 }
1506 }
1507 }
1508 return ""; //$NON-NLS-1$
1509 }
1510
1511 private String getAttributeNameSuggestion(CustomXmlInputElement inputElement) {
1512 Element element = getPreviewElement(inputElement);
1513 if (element != null) {
1514 NamedNodeMap attributeMap = element.getAttributes();
1515 for (int i = 0; i < attributeMap.getLength(); i++) {
1516 Node node = attributeMap.item(i);
1517 boolean unused = true;
1518 if (inputElement.getAttributes() != null) {
1519 for (CustomXmlInputAttribute attribute : inputElement.getAttributes()) {
1520 if (attribute.getAttributeName().equals(node.getNodeName())) {
1521 unused = false;
1522 break;
1523 }
1524 }
1525 }
1526 if (unused) {
1527 return node.getNodeName();
1528 }
1529 }
1530 }
1531 return ""; //$NON-NLS-1$
1532 }
1533
1534 private void validate() {
1535 definition.categoryName = categoryText.getText().trim();
1536 definition.definitionName = logtypeText.getText().trim();
1537 definition.timeStampOutputFormat = timeStampOutputFormatText.getText().trim();
1538
1539 if (selectedElement != null) {
1540 selectedElement.extractInputs();
1541 treeViewer.refresh();
1542 }
1543
1544 List<String> errors = new ArrayList<>();
1545
1546 if (definition.categoryName.length() == 0) {
1547 errors.add(Messages.CustomXmlParserInputWizardPage_emptyCategoryError);
1548 categoryText.setBackground(COLOR_LIGHT_RED);
1549 } else if (definition.definitionName.length() == 0) {
1550 errors.add(Messages.CustomXmlParserInputWizardPage_emptyLogTypeError);
1551 logtypeText.setBackground(COLOR_LIGHT_RED);
1552 } else {
1553 categoryText.setBackground(COLOR_TEXT_BACKGROUND);
1554 logtypeText.setBackground(COLOR_TEXT_BACKGROUND);
1555 if (definition.categoryName.indexOf(':') != -1) {
1556 errors.add(Messages.CustomXmlParserInputWizardPage_invalidCategoryError);
1557 categoryText.setBackground(COLOR_LIGHT_RED);
1558 }
1559 if (definition.definitionName.indexOf(':') != -1) {
1560 errors.add(Messages.CustomXmlParserInputWizardPage_invalidLogTypeError);
1561 logtypeText.setBackground(COLOR_LIGHT_RED);
1562 }
1563 for (TraceTypeHelper helper : TmfTraceType.getTraceTypeHelpers()) {
1564 if (definition.categoryName.equals(helper.getCategoryName()) &&
1565 definition.definitionName.equals(helper.getName()) &&
1566 (editDefinitionName == null || !editDefinitionName.equals(definition.definitionName)) &&
1567 (editCategoryName == null || !editCategoryName.equals(definition.categoryName))) {
1568 errors.add(Messages.CustomXmlParserInputWizardPage_duplicatelogTypeError);
1569 logtypeText.setBackground(COLOR_LIGHT_RED);
1570 break;
1571 }
1572 }
1573 }
1574
1575 if (definition.rootInputElement == null) {
1576 errors.add(Messages.CustomXmlParserInputWizardPage_noDocumentError);
1577 }
1578
1579 if (definition.rootInputElement != null) {
1580 logEntryFound = false;
1581 timeStampFound = false;
1582
1583 errors.addAll(validateElement(definition.rootInputElement));
1584
1585 if ((definition.rootInputElement.getAttributes() != null && definition.rootInputElement.getAttributes().size() != 0)
1586 || (definition.rootInputElement.getChildElements() != null && definition.rootInputElement.getChildElements().size() != 0)
1587 || errors.size() == 0) {
1588 if (!logEntryFound) {
1589 errors.add(Messages.CustomXmlParserInputWizardPage_missingLogEntryError);
1590 }
1591
1592 if (timeStampFound) {
1593 if (timeStampOutputFormatText.getText().trim().length() == 0) {
1594 errors.add(Messages.CustomXmlParserInputWizardPage_missingTimestampFmtError);
1595 timeStampOutputFormatText.setBackground(COLOR_LIGHT_RED);
1596 } else {
1597 try {
1598 new TmfTimestampFormat(timeStampOutputFormatText.getText().trim());
1599 timeStampOutputFormatText.setBackground(COLOR_TEXT_BACKGROUND);
1600 } catch (IllegalArgumentException e) {
1601 errors.add(Messages.CustomXmlParserInputWizardPage_elementInvalidTimestampFmtError);
1602 timeStampOutputFormatText.setBackground(COLOR_LIGHT_RED);
1603 }
1604 }
1605 } else {
1606 timeStampPreviewText.setText(Messages.CustomXmlParserInputWizardPage_noTimestampElementOrAttribute);
1607 }
1608 }
1609 } else {
1610 timeStampPreviewText.setText(Messages.CustomXmlParserInputWizardPage_noTimestampElementOrAttribute);
1611 }
1612
1613 if (errors.size() == 0) {
1614 setDescription(defaultDescription);
1615 setPageComplete(true);
1616 } else {
1617 setDescription(Joiner.on(' ').join(errors));
1618 setPageComplete(false);
1619 }
1620 }
1621
1622 /**
1623 * Clean up the specified XML element.
1624 *
1625 * @param inputElement
1626 * The element to clean up
1627 * @return The validated element
1628 */
1629 public List<String> validateElement(CustomXmlInputElement inputElement) {
1630 List<String> errors = new ArrayList<>();
1631 ElementNode elementNode = null;
1632 if (selectedElement != null && selectedElement.inputElement.equals(inputElement)) {
1633 elementNode = selectedElement;
1634 }
1635 if (inputElement == definition.rootInputElement) {
1636 if (inputElement.getElementName().length() == 0) {
1637 errors.add(Messages.CustomXmlParserInputWizardPage_missingDocumentElementError);
1638 if (elementNode != null) {
1639 elementNode.elementNameText.setBackground(COLOR_LIGHT_RED);
1640 }
1641 } else {
1642 if (elementNode != null) {
1643 elementNode.elementNameText.setBackground(COLOR_TEXT_BACKGROUND);
1644 }
1645 }
1646 }
1647 if (inputElement != definition.rootInputElement) {
1648 if (inputElement.isLogEntry()) {
1649 logEntryFound = true;
1650 }
1651 if (inputElement.getInputTag().equals(Tag.TIMESTAMP)) {
1652 timeStampFound = true;
1653 if (inputElement.getInputFormat().length() == 0) {
1654 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementMissingTimestampFmtError, getName(inputElement)));
1655 if (elementNode != null) {
1656 elementNode.tagText.setBackground(COLOR_LIGHT_RED);
1657 }
1658 } else {
1659 try {
1660 new TmfTimestampFormat(inputElement.getInputFormat());
1661 if (elementNode != null) {
1662 elementNode.tagText.setBackground(COLOR_TEXT_BACKGROUND);
1663 }
1664 } catch (IllegalArgumentException e) {
1665 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementInvalidTimestampFmtError, getName(inputElement)));
1666 if (elementNode != null) {
1667 elementNode.tagText.setBackground(COLOR_LIGHT_RED);
1668 }
1669 }
1670 }
1671 } else if (inputElement.getInputName().length() == 0) {
1672 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementMissingInputNameError, getName(inputElement)));
1673 if (elementNode != null) {
1674 elementNode.tagText.setBackground(COLOR_LIGHT_RED);
1675 }
1676 } else if (inputElement.getInputTag().equals(Tag.OTHER) && Tag.fromLabel(inputElement.getInputName()) != null) {
1677 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementReservedInputNameError, getName(inputElement)));
1678 if (elementNode != null) {
1679 elementNode.tagText.setBackground(COLOR_LIGHT_RED);
1680 }
1681 } else {
1682 if (elementNode != null) {
1683 elementNode.tagText.setBackground(COLOR_TEXT_BACKGROUND);
1684 }
1685 }
1686 if (inputElement.getEventType() != null && inputElement.getEventType().trim().isEmpty()) {
1687 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_emptyEventTypeError, getName(inputElement)));
1688 if (elementNode != null) {
1689 elementNode.eventTypeText.setBackground(COLOR_LIGHT_RED);
1690 }
1691 } else {
1692 if (elementNode != null) {
1693 elementNode.eventTypeText.setBackground(COLOR_TEXT_BACKGROUND);
1694 }
1695 }
1696 }
1697 if (inputElement.getAttributes() != null) {
1698 if (elementNode != null) {
1699 for (Attribute attribute : elementNode.attributes) {
1700 attribute.attributeNameText.setBackground(COLOR_TEXT_BACKGROUND);
1701 }
1702 }
1703 for (int i = 0; i < inputElement.getAttributes().size(); i++) {
1704 CustomXmlInputAttribute attribute = inputElement.getAttributes().get(i);
1705 boolean duplicate = false;
1706 for (int j = i + 1; j < inputElement.getAttributes().size(); j++) {
1707 CustomXmlInputAttribute otherAttribute = inputElement.getAttributes().get(j);
1708 if (otherAttribute.getAttributeName().equals(attribute.getAttributeName())) {
1709 duplicate = true;
1710 if (elementNode != null) {
1711 elementNode.attributes.get(j).attributeNameText.setBackground(COLOR_LIGHT_RED);
1712 }
1713 }
1714 }
1715 if (attribute.getAttributeName().length() == 0) {
1716 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeMissingNameError, getName(inputElement)));
1717 if (elementNode != null) {
1718 elementNode.attributes.get(i).attributeNameText.setBackground(COLOR_LIGHT_RED);
1719 }
1720 } else if (duplicate) {
1721 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeDuplicateNameError, getName(attribute, inputElement)));
1722 if (elementNode != null) {
1723 elementNode.attributes.get(i).attributeNameText.setBackground(COLOR_LIGHT_RED);
1724 }
1725 }
1726 if (attribute.getInputTag().equals(Tag.TIMESTAMP)) {
1727 timeStampFound = true;
1728 if (attribute.getInputFormat().length() == 0) {
1729 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeMissingTimestampFmtError, getName(attribute, inputElement)));
1730 if (elementNode != null) {
1731 elementNode.attributes.get(i).tagText.setBackground(COLOR_LIGHT_RED);
1732 }
1733 } else {
1734 try {
1735 new TmfTimestampFormat(attribute.getInputFormat());
1736 if (elementNode != null) {
1737 elementNode.attributes.get(i).tagText.setBackground(COLOR_TEXT_BACKGROUND);
1738 }
1739 } catch (IllegalArgumentException e) {
1740 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeInvalidTimestampFmtError, getName(attribute, inputElement)));
1741 if (elementNode != null) {
1742 elementNode.attributes.get(i).tagText.setBackground(COLOR_LIGHT_RED);
1743 }
1744 }
1745 }
1746 } else if (attribute.getInputName().length() == 0) {
1747 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeMissingInputNameError, getName(attribute, inputElement)));
1748 if (elementNode != null) {
1749 elementNode.attributes.get(i).tagText.setBackground(COLOR_LIGHT_RED);
1750 }
1751 } else if (attribute.getInputTag().equals(Tag.OTHER) && Tag.fromLabel(attribute.getInputName()) != null) {
1752 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_attributeReservedInputNameError, getName(attribute, inputElement)));
1753 if (elementNode != null) {
1754 elementNode.attributes.get(i).tagText.setBackground(COLOR_LIGHT_RED);
1755 }
1756 } else {
1757 if (elementNode != null) {
1758 elementNode.attributes.get(i).tagText.setBackground(COLOR_TEXT_BACKGROUND);
1759 }
1760 }
1761 }
1762 }
1763 if (inputElement.getChildElements() != null) {
1764 for (CustomXmlInputElement child : inputElement.getChildElements()) {
1765 ElementNode childElementNode = null;
1766 if (selectedElement != null && selectedElement.inputElement.equals(child)) {
1767 childElementNode = selectedElement;
1768 }
1769 if (childElementNode != null) {
1770 childElementNode.elementNameText.setBackground(COLOR_TEXT_BACKGROUND);
1771 }
1772 }
1773 for (int i = 0; i < inputElement.getChildElements().size(); i++) {
1774 CustomXmlInputElement child = inputElement.getChildElements().get(i);
1775 ElementNode childElementNode = null;
1776 if (selectedElement != null && selectedElement.inputElement.equals(child)) {
1777 childElementNode = selectedElement;
1778 }
1779 if (child.getElementName().length() == 0) {
1780 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementMissingNameError, getName(child)));
1781 if (childElementNode != null) {
1782 childElementNode.elementNameText.setBackground(COLOR_LIGHT_RED);
1783 }
1784 } else {
1785 boolean duplicate = false;
1786 for (int j = i + 1; j < inputElement.getChildElements().size(); j++) {
1787 CustomXmlInputElement otherChild = inputElement.getChildElements().get(j);
1788 if (otherChild.getElementName().equals(child.getElementName())) {
1789 duplicate = true;
1790 ElementNode otherChildElementNode = null;
1791 if (selectedElement != null && selectedElement.inputElement.equals(otherChild)) {
1792 otherChildElementNode = selectedElement;
1793 }
1794 if (otherChildElementNode != null) {
1795 otherChildElementNode.elementNameText.setBackground(COLOR_LIGHT_RED);
1796 }
1797 }
1798 }
1799 if (duplicate) {
1800 errors.add(NLS.bind(Messages.CustomXmlParserInputWizardPage_elementDuplicateNameError, getName(child)));
1801 if (childElementNode != null) {
1802 childElementNode.elementNameText.setBackground(COLOR_LIGHT_RED);
1803 }
1804 }
1805 }
1806
1807 errors.addAll(validateElement(child));
1808 }
1809 }
1810 return errors;
1811 }
1812
1813 /**
1814 * Get the trace definition.
1815 *
1816 * @return The trace definition
1817 */
1818 public CustomXmlTraceDefinition getDefinition() {
1819 return definition;
1820 }
1821
1822 /**
1823 * Get the raw text input.
1824 *
1825 * @return The raw text input.
1826 */
1827 public char[] getInputText() {
1828 return inputText.getText().toCharArray();
1829 }
1830 }
This page took 0.1228 seconds and 6 git commands to generate.