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