001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: *
017: */
018:
019: package org.apache.jmeter.protocol.http.gui;
020:
021: import java.awt.BorderLayout;
022: import java.awt.Dimension;
023: import java.awt.event.ActionEvent;
024: import java.awt.event.ActionListener;
025: import java.io.File;
026: import java.io.IOException;
027:
028: import javax.swing.BorderFactory;
029: import javax.swing.JButton;
030: import javax.swing.JPanel;
031: import javax.swing.JScrollPane;
032: import javax.swing.JTable;
033: import javax.swing.ListSelectionModel;
034: import javax.swing.table.AbstractTableModel;
035: import javax.swing.table.TableCellEditor;
036:
037: import org.apache.jmeter.config.gui.AbstractConfigGui;
038: import org.apache.jmeter.gui.util.FileDialoger;
039: import org.apache.jmeter.protocol.http.control.Header;
040: import org.apache.jmeter.protocol.http.control.HeaderManager;
041: import org.apache.jmeter.testelement.TestElement;
042: import org.apache.jmeter.util.JMeterUtils;
043: import org.apache.jorphan.logging.LoggingManager;
044: import org.apache.log.Logger;
045:
046: /**
047: * Allows the user to specify if she needs HTTP header services, and give
048: * parameters for this service.
049: *
050: */
051: public class HeaderPanel extends AbstractConfigGui implements
052: ActionListener {
053: private static final Logger log = LoggingManager
054: .getLoggerForClass();
055:
056: private static final String ADD_COMMAND = "Add"; // $NON-NLS-1$
057:
058: private static final String DELETE_COMMAND = "Delete"; // $NON-NLS-1$
059:
060: private static final String LOAD_COMMAND = "Load"; // $NON-NLS-1$
061:
062: private static final String SAVE_COMMAND = "Save"; // $NON-NLS-1$
063:
064: private InnerTableModel tableModel;
065:
066: private HeaderManager headerManager;
067:
068: private JTable headerTable;
069:
070: private JButton addButton;
071:
072: private JButton deleteButton;
073:
074: private JButton loadButton;
075:
076: private JButton saveButton;
077:
078: public HeaderPanel() {
079: headerManager = new HeaderManager();
080: tableModel = new InnerTableModel(headerManager);
081: init();
082: }
083:
084: public TestElement createTestElement() {
085: configureTestElement(headerManager);
086: return (TestElement) headerManager.clone();
087: }
088:
089: /**
090: * Modifies a given TestElement to mirror the data in the gui components.
091: *
092: * @see org.apache.jmeter.gui.JMeterGUIComponent#modifyTestElement(TestElement)
093: */
094: public void modifyTestElement(TestElement el) {
095: if (headerTable.isEditing()) {// Bug 41905
096: headerTable.getCellEditor().stopCellEditing();
097: }
098: el.clear();
099: el.addTestElement(headerManager);
100: configureTestElement(el);
101: }
102:
103: /**
104: * Implements JMeterGUIComponent.clearGui
105: */
106: public void clearGui() {
107: super .clearGui();
108:
109: tableModel.clearData();
110: deleteButton.setEnabled(false);
111: saveButton.setEnabled(false);
112: }
113:
114: public void configure(TestElement el) {
115: headerManager.clear();
116: super .configure(el);
117: headerManager.addTestElement(el);
118: boolean hasRows = tableModel.getRowCount() > 0;
119: deleteButton.setEnabled(hasRows);
120: saveButton.setEnabled(hasRows);
121:
122: }
123:
124: public String getLabelResource() {
125: return "header_manager_title"; // $NON-NLS-1$
126: }
127:
128: public void init() {
129: setLayout(new BorderLayout());
130: setBorder(makeBorder());
131:
132: add(makeTitlePanel(), BorderLayout.NORTH);
133: add(createHeaderTablePanel(), BorderLayout.CENTER);
134: }
135:
136: public void actionPerformed(ActionEvent e) {
137: String action = e.getActionCommand();
138:
139: if (action.equals(DELETE_COMMAND)) {
140: if (tableModel.getRowCount() > 0) {
141: // If a table cell is being edited, we must cancel the editing
142: // before deleting the row.
143: if (headerTable.isEditing()) {
144: TableCellEditor cellEditor = headerTable
145: .getCellEditor(headerTable.getEditingRow(),
146: headerTable.getEditingColumn());
147: cellEditor.cancelCellEditing();
148: }
149:
150: int rowSelected = headerTable.getSelectedRow();
151:
152: if (rowSelected != -1) {
153: tableModel.removeRow(rowSelected);
154: tableModel.fireTableDataChanged();
155:
156: // Disable the DELETE and SAVE buttons if no rows remaining
157: // after delete
158: if (tableModel.getRowCount() == 0) {
159: deleteButton.setEnabled(false);
160: saveButton.setEnabled(false);
161: }
162:
163: // Table still contains one or more rows, so highlight
164: // (select) the appropriate one.
165: else {
166: int rowToSelect = rowSelected;
167:
168: if (rowSelected >= tableModel.getRowCount()) {
169: rowToSelect = rowSelected - 1;
170: }
171:
172: headerTable.setRowSelectionInterval(
173: rowToSelect, rowToSelect);
174: }
175: }
176: }
177: } else if (action.equals(ADD_COMMAND)) {
178: // If a table cell is being edited, we should accept the current
179: // value and stop the editing before adding a new row.
180: if (headerTable.isEditing()) {
181: TableCellEditor cellEditor = headerTable.getCellEditor(
182: headerTable.getEditingRow(), headerTable
183: .getEditingColumn());
184: cellEditor.stopCellEditing();
185: }
186:
187: tableModel.addNewRow();
188: tableModel.fireTableDataChanged();
189:
190: // Enable the DELETE and SAVE buttons if they are currently
191: // disabled.
192: if (!deleteButton.isEnabled()) {
193: deleteButton.setEnabled(true);
194: }
195: if (!saveButton.isEnabled()) {
196: saveButton.setEnabled(true);
197: }
198:
199: // Highlight (select) the appropriate row.
200: int rowToSelect = tableModel.getRowCount() - 1;
201: headerTable.setRowSelectionInterval(rowToSelect,
202: rowToSelect);
203: } else if (action.equals(LOAD_COMMAND)) {
204: try {
205: File tmp = FileDialoger.promptToOpenFile()
206: .getSelectedFile();
207: if (tmp != null) {
208: headerManager.addFile(tmp.getAbsolutePath());
209: tableModel.fireTableDataChanged();
210:
211: if (tableModel.getRowCount() > 0) {
212: deleteButton.setEnabled(true);
213: saveButton.setEnabled(true);
214: }
215: }
216: } catch (IOException ex) {
217: log.error("Could not load headers", ex);
218: } catch (NullPointerException err) {
219: }
220: } else if (action.equals(SAVE_COMMAND)) {
221: try {
222: File tmp = FileDialoger.promptToSaveFile(null)
223: .getSelectedFile();
224: if (tmp != null) {
225: headerManager.save(tmp.getAbsolutePath());
226: }
227: } catch (IOException ex) {
228: log.error("Could not save headers", ex);
229: } catch (NullPointerException err) {
230: }
231: }
232: }
233:
234: public JPanel createHeaderTablePanel() {
235: // create the JTable that holds header per row
236: headerTable = new JTable(tableModel);
237: headerTable
238: .setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
239: headerTable.setPreferredScrollableViewportSize(new Dimension(
240: 100, 70));
241:
242: JPanel panel = new JPanel(new BorderLayout(0, 5));
243: panel.setBorder(BorderFactory.createTitledBorder(BorderFactory
244: .createEtchedBorder(), JMeterUtils
245: .getResString("headers_stored"))); // $NON-NLS-1$
246: panel.add(new JScrollPane(headerTable), BorderLayout.CENTER);
247: panel.add(createButtonPanel(), BorderLayout.SOUTH);
248: return panel;
249: }
250:
251: private JButton createButton(String resName, char mnemonic,
252: String command, boolean enabled) {
253: JButton button = new JButton(JMeterUtils.getResString(resName));
254: button.setMnemonic(mnemonic);
255: button.setActionCommand(command);
256: button.setEnabled(enabled);
257: button.addActionListener(this );
258: return button;
259: }
260:
261: private JPanel createButtonPanel() {
262: boolean tableEmpty = (tableModel.getRowCount() == 0);
263:
264: addButton = createButton("add", 'A', ADD_COMMAND, true); // $NON-NLS-1$
265: deleteButton = createButton("delete", 'D', DELETE_COMMAND,
266: !tableEmpty); // $NON-NLS-1$
267: loadButton = createButton("load", 'L', LOAD_COMMAND, true); // $NON-NLS-1$
268: saveButton = createButton("save", 'S', SAVE_COMMAND,
269: !tableEmpty); // $NON-NLS-1$
270:
271: JPanel buttonPanel = new JPanel();
272: buttonPanel.add(addButton);
273: buttonPanel.add(deleteButton);
274: buttonPanel.add(loadButton);
275: buttonPanel.add(saveButton);
276: return buttonPanel;
277: }
278:
279: private static class InnerTableModel extends AbstractTableModel {
280: private HeaderManager manager;
281:
282: public InnerTableModel(HeaderManager man) {
283: manager = man;
284: }
285:
286: public void clearData() {
287: manager.clear();
288: fireTableDataChanged();
289: }
290:
291: public void removeRow(int row) {
292: manager.remove(row);
293: }
294:
295: public void addNewRow() {
296: manager.add();
297: }
298:
299: public boolean isCellEditable(int row, int column) {
300: // all table cells are editable
301: return true;
302: }
303:
304: public Class getColumnClass(int column) {
305: return getValueAt(0, column).getClass();
306: }
307:
308: public int getRowCount() {
309: return manager.getHeaders().size();
310: }
311:
312: /**
313: * Required by table model interface.
314: */
315: public int getColumnCount() {
316: return manager.getColumnCount();
317: }
318:
319: /**
320: * Required by table model interface.
321: */
322: public String getColumnName(int column) {
323: return manager.getColumnName(column);
324: }
325:
326: /**
327: * Required by table model interface.
328: */
329: public Object getValueAt(int row, int column) {
330: Header head = manager.getHeader(row);
331: if (column == 0) {
332: return head.getName();
333: } else if (column == 1) {
334: return head.getValue();
335: }
336: return null;
337: }
338:
339: /**
340: * Required by table model interface.
341: */
342: public void setValueAt(Object value, int row, int column) {
343: Header header = manager.getHeader(row);
344:
345: if (column == 0) {
346: header.setName((String) value);
347: } else if (column == 1) {
348: header.setValue((String) value);
349: }
350: }
351:
352: }
353: }
|