/** * The contents of this file are subject to the license and copyright * detailed in the LICENSE and NOTICE files at the root of the source * tree and available online at * * http://www.dspace.org/license/ */ /** * Copyright (c) 2007, Aberystwyth University * * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * - Redistributions of source code must retain the above * copyright notice, this list of conditions and the * following disclaimer. * * - Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * - Neither the name of the Centre for Advanced Software and * Intelligent Systems (CASIS) nor the names of its * contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. */ package org.purl.sword.client; import java.awt.BorderLayout; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.io.File; import javax.swing.DefaultListModel; import javax.swing.JButton; import javax.swing.JCheckBox; import javax.swing.JFileChooser; import javax.swing.JFrame; import javax.swing.JLabel; import javax.swing.JList; import javax.swing.JOptionPane; import javax.swing.JPanel; import javax.swing.JPasswordField; import javax.swing.JScrollPane; import javax.swing.event.ChangeEvent; import javax.swing.event.ChangeListener; /** * Dialog for users to enter details of post destinations. * * @author Neil Taylor */ public class PostDialog implements ActionListener, ChangeListener { /** * label for the browse command. */ protected static final String BROWSE = "browse"; /** * label for the add command. */ protected static final String ADD = "add"; /** * label for the edit command. */ protected static final String EDIT = "edit"; /** * label for the delete command. */ protected static final String DELETE = "delete"; /** * label for the clear command. */ protected static final String CLEAR = "clear"; /** * Username combo box. */ private SWORDComboBox username; /** * Post Location combo box. */ private SWORDComboBox postLocation; /** * Password field. */ private JPasswordField password; /** * The file combo box. */ private SWORDComboBox file; /** * The filetype combo box. */ private SWORDComboBox fileType; /** * The onBehalfOf combo box. */ private SWORDComboBox onBehalfOf; /** * The md5 checkbox. */ private JCheckBox useMD5; /** * The corruptMD5 checkbox. */ private JCheckBox corruptMD5; /** * The corruptRequest checkbox. */ private JCheckBox corruptRequest; /** * The useNoOp checkbox. */ private JCheckBox useNoOp; /** * The verbose checkbox. */ private JCheckBox useVerbose; /** * The format namespace combo box. */ private SWORDComboBox formatNamespace; /** * The list of post destinations. */ private JList list; /** * The parent frame for the dialog that is displayed. */ private JFrame parentFrame = null; /** * Array that lists the labels for the buttons on the panel. */ private static Object[] options = {"Post File", "Cancel" }; /** * The panel that holds the controls to show. */ private JPanel controls = null; /** * * @param parentFrame the parent of this dialog. */ public PostDialog(JFrame parentFrame) { this.parentFrame = parentFrame; controls = createControls(); } /** * Show the dialog with ok and cancel options. * @return The return value from displaying JOptionPane. Either * JOptionPane.OK_OPTION or JOptionPane.CANCEL_OPTION. */ public int show( ) { int result = JOptionPane.showOptionDialog(parentFrame, controls, "Post Document", JOptionPane.OK_CANCEL_OPTION, JOptionPane.PLAIN_MESSAGE, null, options, null); if ( result == JOptionPane.OK_OPTION ) { // update the combo boxes with the values username.updateList(); file.updateList(); fileType.updateList(); onBehalfOf.updateList(); formatNamespace.updateList(); } return result; } /** * Create the controls for the main panel. * * @return The panel. */ protected final JPanel createControls( ) { file = new SWORDComboBox(); JPanel filePanel = new JPanel(new BorderLayout()); filePanel.add(file, BorderLayout.CENTER); JButton browse = new JButton("Browse..."); browse.setActionCommand(BROWSE); browse.addActionListener(this); filePanel.add(browse, BorderLayout.SOUTH); fileType = new SWORDComboBox(); String type = "application/zip"; fileType.addItem(type); fileType.setSelectedItem(type); // controls that will be used in the second dialog postLocation = new SWORDComboBox(); username = new SWORDComboBox(); password = new JPasswordField(); onBehalfOf = new SWORDComboBox(); useMD5 = new JCheckBox(); useMD5.addChangeListener(this); corruptMD5 = new JCheckBox(); corruptRequest = new JCheckBox(); useNoOp = new JCheckBox(); useVerbose = new JCheckBox(); formatNamespace = new SWORDComboBox(); JLabel fileLabel = new JLabel("File:", JLabel.TRAILING); JLabel fileTypeLabel = new JLabel("File Type:", JLabel.TRAILING); JLabel useMD5Label = new JLabel("Use MD5:", JLabel.TRAILING); JLabel corruptMD5Label = new JLabel("Corrupt MD5:", JLabel.TRAILING); JLabel corruptRequestLabel = new JLabel("Corrupt Request:", JLabel.TRAILING); //JLabel corruptMD5Label = new JLabel("Corrupt MD5:", JLabel.TRAILING); JLabel useNoOpLabel = new JLabel("Use noOp:", JLabel.TRAILING); JLabel useVerboseLabel = new JLabel("Use verbose:", JLabel.TRAILING); JLabel formatNamespaceLabel = new JLabel("X-Packaging:", JLabel.TRAILING); JLabel userAgentLabel = new JLabel("User Agent:", JLabel.TRAILING); JLabel userAgentNameLabel = new JLabel(ClientConstants.SERVICE_NAME, JLabel.LEADING); SWORDFormPanel panel = new SWORDFormPanel(); panel.addFirstRow(new JLabel("Please enter the details for the post operation")); JPanel destinations = createDestinationsPanel(); panel.addRow(new JLabel("Destinations:"), destinations); panel.addRow(fileLabel, filePanel); panel.addRow(fileTypeLabel, fileType); panel.addRow(useMD5Label, useMD5); panel.addRow(corruptMD5Label, corruptMD5); panel.addRow(corruptRequestLabel, corruptRequest); panel.addRow(useNoOpLabel, useNoOp); panel.addRow(useVerboseLabel, useVerbose); panel.addRow(formatNamespaceLabel, formatNamespace); panel.addRow(userAgentLabel, userAgentNameLabel); return panel; } /** * Create the destinations panel. This contains a list and four buttons * to operate on values in the list. * * @return The panel containing the controls. */ protected JPanel createDestinationsPanel() { DefaultListModel model = new DefaultListModel(); list = new JList(model); JScrollPane jsp = new JScrollPane(list); JPanel destinations = new JPanel(new BorderLayout()); destinations.add(jsp, BorderLayout.CENTER); JPanel destinationButtons = new JPanel(); JButton addButton = new JButton("Add"); addButton.setActionCommand(ADD); addButton.addActionListener(this); JButton editButton = new JButton("Edit"); editButton.setActionCommand(EDIT); editButton.addActionListener(this); JButton deleteButton = new JButton("Delete"); deleteButton.setActionCommand(DELETE); deleteButton.addActionListener(this); JButton clearButton = new JButton("Clear"); clearButton.setActionCommand(CLEAR); clearButton.addActionListener(this); destinationButtons.add(addButton); destinationButtons.add(editButton); destinationButtons.add(deleteButton); destinationButtons.add(clearButton); destinations.add(destinationButtons, BorderLayout.SOUTH); return destinations; } /** * Handle the button click to select a file to upload. */ public void actionPerformed(ActionEvent evt) { String cmd = evt.getActionCommand(); if ( BROWSE.equals(cmd) ) { JFileChooser chooser = new JFileChooser(); chooser.setCurrentDirectory(new File(System.getProperty("user.dir"))); int returnVal = chooser.showOpenDialog(parentFrame); if (returnVal == JFileChooser.APPROVE_OPTION) { file.setSelectedItem(chooser.getSelectedFile().getAbsolutePath()); } } else if ( ADD.equals(cmd)) { PostDestination dest = showDestinationDialog(null); if ( dest != null ) { ((DefaultListModel)list.getModel()).addElement(dest); } } else if ( EDIT.equals(cmd)) { PostDestination dest = (PostDestination)list.getSelectedValue(); if ( dest != null ) { showDestinationDialog(dest); list.repaint(); } } else if ( DELETE.equals(cmd)) { if ( list.getSelectedIndex() != -1 ) { ((DefaultListModel)list.getModel()).removeElementAt(list.getSelectedIndex()); } } else if ( CLEAR.equals(cmd)) { ((DefaultListModel)list.getModel()).clear(); } } /** * Show the destination dialog. This is used to enter the URL, * username, password and onBehalfOf name for a destination. * * @param destination The post destination. If this is not null, the values * in the object are used to set the current values * in the dialog controls. * @return The post destination value. */ public PostDestination showDestinationDialog( PostDestination destination ) { SWORDFormPanel panel = new SWORDFormPanel(); panel.addFirstRow(new JLabel("Please enter the details for the post operation")); JLabel postLabel = new JLabel("Post Location:", JLabel.TRAILING); JLabel userLabel = new JLabel("Username:", JLabel.TRAILING); JLabel passwordLabel = new JLabel("Password:", JLabel.TRAILING); JLabel onBehalfOfLabel = new JLabel("On Behalf Of:", JLabel.TRAILING); panel.addRow(postLabel, postLocation); panel.addRow(userLabel, username); panel.addRow(passwordLabel, password); panel.addRow(onBehalfOfLabel, onBehalfOf); if ( destination != null ) { postLocation.insertItem(destination.getUrl()); username.insertItem(destination.getUsername()); password.setText(destination.getPassword()); onBehalfOf.insertItem(destination.getOnBehalfOf()); } else { String s = ""; postLocation.insertItem(s); //postLocation.setSelectedItem(s); username.insertItem(s); username.setSelectedItem(s); password.setText(s); onBehalfOf.insertItem(s); onBehalfOf.setSelectedItem(s); } int result = JOptionPane.showOptionDialog(null, panel, "Destination", JOptionPane.OK_CANCEL_OPTION, JOptionPane.PLAIN_MESSAGE, null, new String[] { "OK", "Cancel" }, null); if ( result == JOptionPane.OK_OPTION ) { postLocation.updateList(); username.updateList(); onBehalfOf.updateList(); if ( destination == null ) { destination = new PostDestination(); } destination.setUrl(postLocation.getText()); destination.setUsername(username.getText()); String pass = new String(password.getPassword()); if ( pass.length() > 0 ) { destination.setPassword(pass); } else { destination.setPassword(null); } String obo = onBehalfOf.getText(); if ( obo.length() > 0 ) { destination.setOnBehalfOf(onBehalfOf.getText()); } else { destination.setOnBehalfOf(null); } } return destination; } /** * Get the list of Post Destinations. * @return The destinations. */ public PostDestination[] getDestinations() { DefaultListModel model = (DefaultListModel)list.getModel(); PostDestination[] destinations = new PostDestination[model.size()]; for ( int i = 0; i < model.size(); i++) { destinations[i] = (PostDestination)model.get(i); } return destinations; } /** * Get the file details. * @return The value. */ public String getFile( ) { return file.getText(); } /** * Get the filetype value. * @return The value. */ public String getFileType() { return fileType.getText(); } /** * Get the onBehalfOf value. * @return The value. */ public String getOnBehalfOf() { return onBehalfOf.getText(); } /** * Get the format namespace value. * @return The value. */ public String getFormatNamespace() { return formatNamespace.getText(); } /** * Determine if the MD5 checkbox is selected. * * @return True if the MD5 checkbox is selected. */ public boolean useMd5() { return useMD5.isSelected(); } /** * Determine if the noOp checkbox is selected. * * @return True if the checkbox is selected. */ public boolean useNoOp() { return useNoOp.isSelected(); } /** * Determine if the verbose checkbox is selected. * * @return True if the checkbox is selected. */ public boolean useVerbose() { return useVerbose.isSelected(); } /** * Get the post location. * @return The post location. */ public String getPostLocation() { return postLocation.getText(); } /** * Determine if the MD5 hash should be corrupted. * @return True if the corrupt MD5 checkbox is selected. The MD5 checkbox * must also be selected. */ public boolean corruptMD5() { return (corruptMD5.isEnabled() && corruptMD5.isSelected()); } /** * Determine if the POST request should be corrupted. * @return True if the corrupt request checkbox is selected. */ public boolean corruptRequest() { return (corruptRequest.isSelected()); } /** * Detect a state change event for the checkbox. * * @param evt The event. */ public void stateChanged(ChangeEvent evt) { corruptMD5.setEnabled(useMD5.isSelected()); } /** * Add a list of user ids. * * @param users The user ids. */ public void addUserIds(String[] users) { username.insertItems(users); } /** * Add a list of deposit URLs. * * @param deposits The URLs. */ public void addDepositUrls(String[] deposits) { postLocation.insertItems(deposits); } /** * Add a list of onBehalfOf names. * * @param users The names. */ public void addOnBehalfOf(String[] users) { onBehalfOf.insertItems(users); } /** * Add the list of formatNamespace strings. * * @param namespaces list of strings. */ public void addFormatNamespaces(String[] namespaces) { formatNamespace.insertItems(namespaces); } /** * Add a list of file types. * * @param types The file types. */ public void addFileTypes(String[] types) { fileType.insertItems(types); } /** * Add a list of file names. * @param files The list of files. */ public void addFiles(String[] files) { file.insertItems(files); } /** * Set the deposit location. * * @param location The location. */ public void setDepositLocation(String location) { postLocation.insertItem(location); postLocation.setSelectedItem(location); } }