Package org.wiztools.restclient.ui

Source Code of org.wiztools.restclient.ui.RESTView

package org.wiztools.restclient.ui;

import com.jidesoft.swing.AutoCompletion;
import java.awt.event.FocusEvent;
import org.wiztools.restclient.*;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.Toolkit;
import java.awt.datatransfer.Clipboard;
import java.awt.datatransfer.StringSelection;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusAdapter;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
import java.util.LinkedList;
import javax.swing.ButtonGroup;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JProgressBar;
import javax.swing.JRadioButton;
import javax.swing.JScrollPane;
import javax.swing.JTabbedPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.BorderFactory;
import javax.swing.ImageIcon;
import javax.swing.JCheckBox;
import javax.swing.JEditorPane;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JPasswordField;
import javax.swing.JPopupMenu;
import javax.swing.JSeparator;
import javax.swing.JSplitPane;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
import javax.swing.border.TitledBorder;
import junit.framework.TestSuite;
import org.wiztools.commons.Charsets;
import org.wiztools.commons.CollectionsUtil;
import org.wiztools.commons.FileUtil;
import org.wiztools.restclient.TestException;
import org.wiztools.restclient.TestResult;
import org.wiztools.restclient.TestUtil;
import org.wiztools.restclient.XMLException;
import org.wiztools.restclient.XMLUtil;
import org.wiztools.commons.Implementation;
import org.wiztools.commons.MultiValueMap;
import org.wiztools.commons.StringUtil;

/**
*
* @author Subhash
*/
class RESTView extends JPanel implements View {
    private static final Logger LOG = Logger.getLogger(RESTView.class.getName());
   
    private ImageIcon icon_go = UIUtil.getIconFromClasspath("org/wiztools/restclient/go.png");
    private ImageIcon icon_stop = UIUtil.getIconFromClasspath("org/wiztools/restclient/stop.png");
   
    private JRadioButton jrb_req_get = new JRadioButton("GET");
    private JRadioButton jrb_req_post = new JRadioButton("POST");
    private JRadioButton jrb_req_put = new JRadioButton("PUT");
    private JRadioButton jrb_req_delete = new JRadioButton("DELETE");
    private JRadioButton jrb_req_head = new JRadioButton("HEAD");
    private JRadioButton jrb_req_options = new JRadioButton("OPTIONS");
    private JRadioButton jrb_req_trace = new JRadioButton("TRACE");
   
    private JProgressBar jpb_status = new JProgressBar();
   
    private JLabel jl_status = new JLabel(RCConstants.TITLE);
    private JLabel jl_url = new JLabel("URL: ");
    private boolean fromKeyboard = false;
    private JComboBox jcb_url = new JComboBox();
   
    private JButton jb_request = null;
   
    private JTextField jtf_res_status = new JTextField();
   
    private JTextField jtf_body_content_type = new JTextField();
    private ScriptEditor se_req_body;
    {
        IGlobalOptions options = Implementation.of(IGlobalOptions.class);
        final boolean enableSyntaxColoring = Boolean.valueOf(
                options.getProperty("request.body.syntax.color")==null?
                    "true": options.getProperty("request.body.syntax.color"));
        if(enableSyntaxColoring) {
            se_req_body = ScriptEditorFactory.getXMLScriptEditor();
        }
        else {
            se_req_body = ScriptEditorFactory.getTextAreaScriptEditor();
        }
    }
    private JButton jb_body_content_type = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "edit.png"));
    private JButton jb_body_file = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "load_from_file.png"));
    private JButton jb_body_params = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "insert_parameters.png"));
    private BodyContentTypeDialog jd_body_content_type;
   
    // private JScrollPane jsp_test_script;
    private ScriptEditor se_test_script = ScriptEditorFactory.getGroovyScriptEditor();
    private JButton jb_req_test_template = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "insert_template.png"));
    private JButton jb_req_test_open = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "load_from_file.png"));
    private JButton jb_req_test_run = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "wand.png"));
    private JButton jb_req_test_quick = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "quick_test.png"));
    private RunTestDialog jd_runTestDialog;
   
    // Authentication resources
    private JCheckBox jcb_auth_basic = new JCheckBox("BASIC");
    private JCheckBox jcb_auth_digest = new JCheckBox("DIGEST");
    private JCheckBox jcb_auth_preemptive = new JCheckBox("Preemptive");
    private JLabel jl_auth_host = new JLabel("<html>Host: </html>");
    private JLabel jl_auth_realm = new JLabel("<html>Realm: </html>");
    private JLabel jl_auth_username = new JLabel("<html>Username: <font color=red>*</font></html>");
    private JLabel jl_auth_password = new JLabel("<html>Password: <font color=red>*</font></html>");
    private static final int auth_text_size = 20;
    private JTextField jtf_auth_host = new JTextField(auth_text_size);
    private JTextField jtf_auth_realm = new JTextField(auth_text_size);
    private JTextField jtf_auth_username = new JTextField(auth_text_size);
    private JPasswordField jpf_auth_password = new JPasswordField(auth_text_size);
   
    // SSL
    private JTextField jtf_ssl_truststore_file = new JTextField(auth_text_size);
    private JButton jb_ssl_browse = new JButton(UIUtil.getIconFromClasspath(RCFileView.iconBasePath + "load_from_file.png"));
    private JPasswordField jpf_ssl_truststore_pwd = new JPasswordField(auth_text_size);
    private JComboBox jcb_ssl_hostname_verifier = new JComboBox(SSLHostnameVerifier.getAll());
   
    // HTTP Version Combo box
    private JComboBox jcb_http_version = new JComboBox(HTTPVersion.values());

    // Follow redirect
    private JCheckBox jcb_followRedirects = new JCheckBox("Follow HTTP Redirects? ");
   
    // Response
    // private JScrollPane jsp_res_body = new JScrollPane();
    private ScriptEditor se_response;
    {
        IGlobalOptions options = Implementation.of(IGlobalOptions.class);
        final boolean enableSyntaxColoring = Boolean.valueOf(
                options.getProperty("response.body.syntax.color")==null?
                    "true": options.getProperty("response.body.syntax.color"));
        if(enableSyntaxColoring) {
            se_response = ScriptEditorFactory.getXMLScriptEditor();
        }
        else {
            se_response = ScriptEditorFactory.getTextAreaScriptEditor();
        }
    }
   
    private JTable jt_res_headers = new JTable();

    //private JScrollPane jsp_test_result;
    //private JTextArea jta_test_result = new JTextArea();
    private TestResultPanel jp_testResultPanel = new TestResultPanel();

    private TwoColumnTablePanel jp_2col_req_headers;
   
    private ParameterDialog jd_req_paramDialog;
   
    private ResponseHeaderTableModel resHeaderTableModel = new ResponseHeaderTableModel();
   
    // Session Details
    SessionFrame sessionFrame = new SessionFrame("RESTClient: Session View");

    private MessageDialog messageDialog;
    private final RESTView view;
    private final RESTUserInterface rest_ui;
   
    public static final int BORDER_WIDTH = 5;

    // RequestThread
    private Thread requestThread;

    /*
     * unindentedResponseBody holds the unindented version of the response body
     * text which is shown in UI currently. This variable should be carefully
     * be dealt with, as wrong handling could make this value stale.
     */
    private String unindentedResponseBody;
   
    // Cache the last request and response
    private Request lastRequest;
    private Response lastResponse;
   
    // Load templateTestScript:
    private static final String templateTestScript;
    static{
        InputStream is = RESTView.class.getClassLoader().getResourceAsStream("org/wiztools/restclient/test-script.template");
        String t = null;
        try{
            BufferedReader br = new BufferedReader(new InputStreamReader(is));
            String str = null;
            StringBuilder sb = new StringBuilder();
            while((str = br.readLine()) != null){
                sb.append(str).append("\n");
            }
            br.close();
            t = sb.toString();
        }
        catch(IOException ex){
            assert true: "Failed loading `test-script.template'!";
        }
        templateTestScript = t;
    }

    protected RESTView(final RESTUserInterface ui){
        this(ui, null, null);
    }

    public RESTView(final RESTUserInterface ui, ScriptEditor scriptEditor, ScriptEditor responseViewer) {
        if (scriptEditor != null)
            this.se_test_script = scriptEditor;
        if (responseViewer != null)
            this.se_response = responseViewer;
        this.rest_ui = ui;
        init();
        view = this;
       
        // Start status clear timer:
        statusLastUpdated = Calendar.getInstance();
        new Timer(5*1000, new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                Calendar c = (Calendar)statusLastUpdated.clone();
                c.add(Calendar.SECOND, 20);
                if(Calendar.getInstance().after(c)){
                    setStatusMessage(RCConstants.TITLE);
                }
            }
        }).start();
    }
   
    private JTabbedPane initJTPRequest(){
        JTabbedPane jtp = new JTabbedPane();
       
        ButtonGroup bg = new ButtonGroup();
        bg.add(jrb_req_get);
        bg.add(jrb_req_post);
        bg.add(jrb_req_put);
        bg.add(jrb_req_delete);
        bg.add(jrb_req_head);
        bg.add(jrb_req_options);
        bg.add(jrb_req_trace);
       
        // Default selected button
        jrb_req_get.setSelected(true);
       
        // Mnemonic
        jrb_req_get.setMnemonic('g');
        jrb_req_post.setMnemonic('p');
        jrb_req_put.setMnemonic('t');
        jrb_req_delete.setMnemonic('d');
        //jrb_req_head.setMnemonic('h');
        //jrb_req_options.setMnemonic('o');
        //jrb_req_trace.setMnemonic('e');
       
        ActionListener jrbAL = new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                if(jrb_req_post.isSelected() || jrb_req_put.isSelected()){
                    setUIReqBodyEnabled(true);
                }
                else{
                    setUIReqBodyEnabled(false);
                }
            }
        };
       
        jrb_req_get.addActionListener(jrbAL);
        jrb_req_post.addActionListener(jrbAL);
        jrb_req_put.addActionListener(jrbAL);
        jrb_req_delete.addActionListener(jrbAL);
        jrb_req_head.addActionListener(jrbAL);
        jrb_req_options.addActionListener(jrbAL);
        jrb_req_trace.addActionListener(jrbAL);
       
        JPanel jp_method_encp = new JPanel();
        jp_method_encp.setLayout(new FlowLayout(FlowLayout.LEFT));
        JPanel jp_method = new JPanel();
        jp_method.setBorder(BorderFactory.createTitledBorder("HTTP Method"));
        jp_method.setLayout(new GridLayout(4, 2));
        jp_method.add(jrb_req_get);
        jp_method.add(jrb_req_post);
        jp_method.add(jrb_req_put);
        jp_method.add(jrb_req_delete);
        jp_method.add(jrb_req_head);
        jp_method.add(jrb_req_options);
        jp_method.add(jrb_req_trace);
        jp_method_encp.add(jp_method);
        jtp.addTab("Method", jp_method_encp);
       
        // Headers Tab
        jp_2col_req_headers = new TwoColumnTablePanel(new String[]{"Header", "Value"}, rest_ui);
        jtp.addTab("Headers", jp_2col_req_headers);
       
        // Body Tab
        setUIReqBodyEnabled(false); // disable control by default
        JPanel jp_body = new JPanel();
        jp_body.setLayout(new BorderLayout());
        JPanel jp_body_north = new JPanel();
        jp_body_north.setLayout(new FlowLayout(FlowLayout.LEFT));
       
        jtf_body_content_type.setEditable(false);
        jtf_body_content_type.setColumns(24);
        jtf_body_content_type.setToolTipText("Selected Content-type & Charset");
        jtf_body_content_type.setText(Util.getFormattedContentType(
                jd_body_content_type.getContentType(),
                jd_body_content_type.getCharSet()));
        jp_body_north.add(jtf_body_content_type);
   
        jb_body_content_type.setToolTipText("Edit Content-type & Charset");
        jb_body_content_type.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                jd_body_content_type.setVisible(true);
            }
        });
        jp_body_north.add(jb_body_content_type);
       
        JSeparator js = new JSeparator(SwingConstants.VERTICAL);
        jp_body_north.add(js);
       
        jb_body_file.setToolTipText("Load from file");
        jb_body_file.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                jb_body_fileActionPerformed(event);
            }
        });
        jp_body_north.add(jb_body_file);
       
        jb_body_params.setToolTipText("Insert parameters");
        jb_body_params.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                jb_body_paramActionPerformed(event);
            }
        });
        jp_body_north.add(jb_body_params);
       
        // Popup menu for body content tab
        final JPopupMenu jpm_req_body = new JPopupMenu();
       
        JMenu jm_syntax = new JMenu("Syntax Color");
        JMenuItem jmi_syntax_none = new JMenuItem("None");
        jmi_syntax_none.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_req_body, TextEditorSyntax.DEFAULT);
            }
        });
        jm_syntax.add(jmi_syntax_none);
        JMenuItem jmi_syntax_xml = new JMenuItem("XML");
        jmi_syntax_xml.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_req_body, TextEditorSyntax.XML);
            }
        });
        jm_syntax.add(jmi_syntax_xml);
        JMenuItem jmi_syntax_json = new JMenuItem("JSON");
        jmi_syntax_json.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_req_body, TextEditorSyntax.JSON);
            }
        });
        jm_syntax.add(jmi_syntax_json);
       
        jpm_req_body.add(jm_syntax);
       
        if (se_req_body.getEditorComponent() instanceof JEditorPane) {
            se_req_body.getEditorComponent().addMouseListener(new MouseAdapter() {
                @Override
                public void mousePressed(MouseEvent e) {
                    showPopup(e);
                }

                @Override
                public void mouseReleased(MouseEvent e) {
                    showPopup(e);
                }
                private void showPopup(final MouseEvent e) {
                    if(!se_req_body.getEditorComponent().isEnabled()){
                        // do not show popup menu when component is disabled:
                        return;
                    }
                    if (e.isPopupTrigger()) {
                        jpm_req_body.show(e.getComponent(), e.getX(), e.getY());
                    }
                }
            });
        }
       
        jp_body.add(jp_body_north, BorderLayout.NORTH);
        JPanel jp_body_center = new JPanel();
        jp_body_center.setLayout(new GridLayout(1, 1));
        jp_body_center.add(se_req_body.getEditorView());
        jp_body.add(jp_body_center, BorderLayout.CENTER);
        jtp.addTab("Body", jp_body);
       
        // Auth Tab
        JPanel jp_auth = new JPanel();
        jp_auth.setLayout(new BorderLayout());
        JPanel jp_auth_west = new JPanel();
        jp_auth_west.setLayout(new BorderLayout());
        JPanel jp_auth_west_center = new JPanel();
        jp_auth_west_center.setBorder(BorderFactory.createTitledBorder("Auth Type"));
        jp_auth_west_center.setLayout(new GridLayout(2,1));
        jcb_auth_basic.setSelected(false);
        ActionListener action = new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                auth_enableActionPerformed(event);
            }
        };
        jcb_auth_basic.addActionListener(action);
        jcb_auth_digest.addActionListener(action);
        jp_auth_west_center.add(jcb_auth_basic);
        jp_auth_west_center.add(jcb_auth_digest);
        jp_auth_west.add(jp_auth_west_center, BorderLayout.CENTER);
        JPanel jp_auth_west_south = new JPanel();
        jp_auth_west_south.setBorder(BorderFactory.createTitledBorder("Preemptive?"));
        jp_auth_west_south.setLayout(new GridLayout(1, 1));
        jcb_auth_preemptive.setToolTipText("Send authentication credentials before challenge");
        jcb_auth_preemptive.setSelected(true);
        jcb_auth_preemptive.setEnabled(false);
        jp_auth_west_south.add(jcb_auth_preemptive);
        jp_auth_west.add(jp_auth_west_south, BorderLayout.SOUTH);
        jp_auth.add(jp_auth_west, BorderLayout.WEST);
        JPanel jp_auth_center = new JPanel();
        jp_auth_center.setBorder(BorderFactory.createTitledBorder("Details"));
        jp_auth_center.setLayout(new BorderLayout());
        JPanel jp_auth_center_west = new JPanel();
        jp_auth_center_west.setLayout(new GridLayout(4, 1, BORDER_WIDTH, BORDER_WIDTH));
        jl_auth_host.setEnabled(false);
        jl_auth_realm.setEnabled(false);
        jl_auth_username.setEnabled(false);
        jl_auth_password.setEnabled(false);
        jp_auth_center_west.add(jl_auth_host);
        jp_auth_center_west.add(jl_auth_realm);
        jp_auth_center_west.add(jl_auth_username);
        jp_auth_center_west.add(jl_auth_password);
        jp_auth_center.add(jp_auth_center_west, BorderLayout.WEST);
        JPanel jp_auth_center_center = new JPanel();
        jp_auth_center_center.setLayout(new GridLayout(4, 1, BORDER_WIDTH, BORDER_WIDTH));
        jtf_auth_host.setEnabled(false);
        jtf_auth_realm.setEnabled(false);
        jtf_auth_username.setEnabled(false);
        jpf_auth_password.setEnabled(false);
        jp_auth_center_center.add(jtf_auth_host);
        jp_auth_center_center.add(jtf_auth_realm);
        jp_auth_center_center.add(jtf_auth_username);
        jp_auth_center_center.add(jpf_auth_password);
        jp_auth_center.add(jp_auth_center_center, BorderLayout.CENTER);
        jp_auth.add(jp_auth_center, BorderLayout.CENTER);
        JPanel jp_auth_encp = new JPanel();
        jp_auth_encp.setLayout(new FlowLayout(FlowLayout.LEFT));
        jp_auth_encp.add(jp_auth);
        jtp.addTab("Auth", jp_auth_encp);
       
        // SSL Tab
        JPanel jp_ssl = new JPanel();
        jp_ssl.setLayout(new BorderLayout(BORDER_WIDTH, 2));
        // SSL West
        JPanel jp_ssl_west = new JPanel();
        jp_ssl_west.setLayout(new GridLayout(3, 1));
        jp_ssl_west.add(UIUtil.getFlowLayoutPanelLeftAligned(new JLabel("Trust store file:")));
        jp_ssl_west.add(UIUtil.getFlowLayoutPanelLeftAligned(new JLabel("Trust store password:")));
        jp_ssl_west.add(UIUtil.getFlowLayoutPanelLeftAligned(new JLabel("Hostname verifier:")));
        jp_ssl.add(jp_ssl_west, BorderLayout.WEST);
        // SSL Center
        JPanel jp_ssl_center = new JPanel();
        jp_ssl_center.setLayout(new GridLayout(3, 1));
        JPanel jp_ssl_center_flow = UIUtil.getFlowLayoutPanelLeftAligned(jtf_ssl_truststore_file);
        jb_ssl_browse.setToolTipText("Open truststore file.");
        jb_ssl_browse.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                File f = rest_ui.getOpenFile(FileChooserType.OPEN_GENERIC);
                if(f == null){
                    // do nothing--cancel pressed
                }
                else if(f.canRead()){
                    jtf_ssl_truststore_file.setText(f.getAbsolutePath());
                }
                else{
                    setStatusMessage("Truststore file cannot be read.");
                }
            }
        });
        jp_ssl_center_flow.add(jb_ssl_browse);
        jp_ssl_center.add(jp_ssl_center_flow);
        jp_ssl_center.add(UIUtil.getFlowLayoutPanelLeftAligned(jpf_ssl_truststore_pwd));
        jp_ssl_center.add(UIUtil.getFlowLayoutPanelLeftAligned(jcb_ssl_hostname_verifier));
        jp_ssl.add(jp_ssl_center, BorderLayout.CENTER);
        jtp.addTab("SSL", UIUtil.getFlowLayoutPanelLeftAligned("SSL Trust Store Configuration", jp_ssl));
       
        // Etc panel
        JPanel jp_etc = new JPanel();
        jp_etc.setLayout(new GridLayout(2, 1));
        { // Http Version
            JPanel jp = new JPanel(new FlowLayout(FlowLayout.LEFT));
            jp.add(new JLabel("HTTP Version: "));
            jp.add(jcb_http_version);
            jp_etc.add(jp);
        }
        { // Follow Redirect
            JPanel jp = new JPanel(new FlowLayout(FlowLayout.LEFT));
            // Previous version of RESTClient had follow redirects as true.
            // To maintain backward compatibility in default behavior:
            jcb_followRedirects.setSelected(true);
            jcb_followRedirects.setHorizontalTextPosition(SwingConstants.LEFT);
            jcb_followRedirects.setBorder(null);
            jp.add(jcb_followRedirects);
            jp_etc.add(jp);
        }
        { // add jp_etc in an enclosing panel
            JPanel jp = new JPanel(new FlowLayout(FlowLayout.LEFT));
            jp.add(jp_etc);
            jtp.add("Etc.", jp);
        }
       
        // Test script panel
        JPanel jp_test = new JPanel();
        jp_test.setLayout(new BorderLayout());
       
        JPanel jp_test_north = new JPanel();
        jp_test_north.setLayout(new FlowLayout(FlowLayout.LEFT));
        jb_req_test_template.setToolTipText("Insert Template");
        jb_req_test_template.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                String t = se_test_script.getText();
                if(!StringUtil.isStrEmpty(t)){
                    JOptionPane.showMessageDialog(rest_ui.getFrame(),
                            "Script text already present! Please clear existing script!",
                            "Error", JOptionPane.ERROR_MESSAGE);
                    return;
                }
                se_test_script.setText(templateTestScript);
                se_test_script.setCaretPosition(0);
            }
        });
        jp_test_north.add(jb_req_test_template);
        jb_req_test_open.setToolTipText("Open Test Script From File");
        jb_req_test_open.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                String str = se_test_script.getText();
                if(!StringUtil.isStrEmpty(str)){
                    int ret = JOptionPane.showConfirmDialog(rest_ui.getFrame(), "Script already exists. Erase?", "Erase existing script?", JOptionPane.YES_NO_OPTION);
                    if(ret == JOptionPane.NO_OPTION){
                        return;
                    }
                }
                File f = rest_ui.getOpenFile(FileChooserType.OPEN_TEST_SCRIPT);
                if(f == null){ // Cancel pressed
                    return;
                }
                if(!f.canRead()){
                    JOptionPane.showMessageDialog(rest_ui.getFrame(),
                            "IO Error (Read permission denied): " + f.getAbsolutePath(),
                            "IO Error", JOptionPane.ERROR_MESSAGE);
                    return;
                }
                try{
                    String testScript = FileUtil.getContentAsString(f, Charsets.UTF_8);
                    se_test_script.setText(testScript);
                    se_test_script.setCaretPosition(0);
                }
                catch(IOException ex){
                    showError(Util.getStackTrace(ex));
                }
            }
        });
        jp_test_north.add(jb_req_test_open);
        jp_test_north.add(new JSeparator(JSeparator.VERTICAL));
        jb_req_test_run.setToolTipText("Run Test");
        jb_req_test_run.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                if(StringUtil.isStrEmpty(se_test_script.getText())){
                    JOptionPane.showMessageDialog(rest_ui.getFrame(),
                            "No script!", "Error", JOptionPane.ERROR_MESSAGE);
                    return;
                }
                if(jd_runTestDialog == null){
                    jd_runTestDialog = new RunTestDialog(rest_ui);
                }
                jd_runTestDialog.setVisible(true);
            }
        });
        jp_test_north.add(jb_req_test_run);
        jb_req_test_quick.setToolTipText("Quick Run Test-Using last request & response");
        jb_req_test_quick.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                if(lastRequest == null || lastResponse == null){
                    JOptionPane.showMessageDialog(rest_ui.getFrame(), "No Last Request/Response", "Error", JOptionPane.ERROR_MESSAGE);
                    return;
                }
                String testScript = se_test_script.getText();
                if(StringUtil.isStrEmpty(testScript)){
                    JOptionPane.showMessageDialog(rest_ui.getFrame(), "No Script", "Error", JOptionPane.ERROR_MESSAGE);
                    return;
                }
                runClonedRequestTest(lastRequest, lastResponse);
            }
        });
        jp_test_north.add(jb_req_test_quick);
        jp_test.add(jp_test_north, BorderLayout.NORTH);
       
        jp_test.add(se_test_script.getEditorView(), BorderLayout.CENTER);
        jtp.addTab("Test Script", jp_test);
       
        return jtp;
    }
   
    void runClonedRequestTest(Request request, Response response){
        RequestBean t_request = (RequestBean)request.clone();
        t_request.setTestScript(se_test_script.getText());
        try{
            TestSuite ts = TestUtil.getTestSuite(t_request, response);
            TestResult testResult = TestUtil.execute(ts);
            view.showMessage("Test Result", testResult.toString());
        }
        catch(TestException ex){
            view.showError(Util.getStackTrace(ex));
        }
    }
   
    private void actionTextEditorSyntaxChange(final ScriptEditor editor, final TextEditorSyntax syntax){
        ((JSyntaxPaneScriptEditor)editor).setSyntax(syntax);
    }
   
    private JTabbedPane initJTPResponse(){
        JTabbedPane jtp = new JTabbedPane();
       
        // Header Tab
        JPanel jp_headers = new JPanel();
        jp_headers.setLayout(new BorderLayout());
       
        // Header Tab: Other Headers
        JPanel jp_headers_others = new JPanel();
        jp_headers_others.setLayout(new GridLayout(1, 1));
        jt_res_headers.addMouseListener(new MouseAdapter() {
            private JPopupMenu popup = new JPopupMenu();
            private JMenuItem jmi_copy = new JMenuItem("Copy Selected Header(s)");
            private JMenuItem jmi_copy_all = new JMenuItem("Copy All Headers");
            {
                jmi_copy.addActionListener(new ActionListener() {
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        final int[] rows = jt_res_headers.getSelectedRows();
                        Arrays.sort(rows);
                        StringBuilder sb = new StringBuilder();
                        for(final int row: rows) {
                            final String key = (String) jt_res_headers.getValueAt(row, 0);
                            final String value = (String) jt_res_headers.getValueAt(row, 1);
                            sb.append(key).append(": ").append(value).append("\r\n");
                        }
                        UIUtil.clipboardCopy(sb.toString());
                    }
                });
                popup.add(jmi_copy);

                jmi_copy_all.addActionListener(new ActionListener() {
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        final int totalRows = jt_res_headers.getRowCount();

                        StringBuilder sb = new StringBuilder();
                        for(int i=0; i<totalRows; i++) {
                            final String key = (String) jt_res_headers.getValueAt(i, 0);
                            final String value = (String) jt_res_headers.getValueAt(i, 1);

                            sb.append(key).append(": ").append(value).append("\r\n");
                        }
                        UIUtil.clipboardCopy(sb.toString());
                    }
                });
                popup.add(jmi_copy_all);
            }

            @Override
            public void mousePressed(MouseEvent e) {
                showPopup(e);
            }

            @Override
            public void mouseReleased(MouseEvent e) {
                showPopup(e);
            }

            private void showPopup(MouseEvent e) {
                if(jt_res_headers.getSelectedRowCount() == 0) {
                    jmi_copy.setEnabled(false);
                }
                else {
                    jmi_copy.setEnabled(true);
                }
                if (e.isPopupTrigger()) {
                    popup.show(e.getComponent(), e.getX(), e.getY());
                }
            }
        });
        jt_res_headers.setModel(resHeaderTableModel);
        JScrollPane jsp = new JScrollPane(jt_res_headers);
        Dimension d = jsp.getPreferredSize();
        d.height = d.height / 2;
        jsp.setPreferredSize(d);
        jp_headers_others.add(jsp);
        jp_headers.add(jp_headers_others, BorderLayout.CENTER);
        jtp.addTab("Headers", jp_headers);
       
        // Response body
        // First the pop-up menu for xml formatting:
        final JPopupMenu popupMenu = new JPopupMenu();
       
        JMenu jm_indent = new JMenu("Indent");
       
        // Indent XML
        JMenuItem jmi_indentXml = new JMenuItem("Indent XML");
        jmi_indentXml.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent evt) {
                String resText = se_response.getText();
                if("".equals(resText.trim())){
                    setStatusMessage("No response body!");
                    return;
                }
                try {
                    final String indentedXML = XMLUtil.indentXML(resText);
                    se_response.setText(indentedXML);
                    se_response.setCaretPosition(0);
                    setStatusMessage("Indent XML: Success");
                } catch (XMLException ex) {
                    setStatusMessage("Indent XML: XML Parser Configuration Error.");
                } catch (IOException ex) {
                    setStatusMessage("Indent XML: IOError while processing XML.");
                }
            }
        });
        jm_indent.add(jmi_indentXml);
       
        // Indent JSON
        JMenuItem jmi_indentJson = new JMenuItem("Indent JSON");
        jmi_indentJson.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                String resText = se_response.getText();
                if("".equals(resText.trim())){
                    setStatusMessage("No response body!");
                    return;
                }
                try{
                    String indentedJSON = JSONUtil.indentJSON(resText);
                    se_response.setText(indentedJSON);
                    se_response.setCaretPosition(0);
                    setStatusMessage("Indent JSON: Success");
                }
                catch(JSONUtil.JSONParseException ex){
                    setStatusMessage("Indent JSON: Not a valid JSON text.");
                }
            };
        });
        jm_indent.add(jmi_indentJson);
       
        popupMenu.add(jm_indent);
       
        // Syntax color change
        JMenu jm_syntax = new JMenu("Syntax Color");
        JMenuItem jmi_syntax_xml = new JMenuItem("XML");
        jmi_syntax_xml.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_response, TextEditorSyntax.XML);
            }
        });
        jm_syntax.add(jmi_syntax_xml);
        JMenuItem jmi_syntax_json = new JMenuItem("JSON");
        jmi_syntax_json.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_response, TextEditorSyntax.JSON);
            }
        });
        jm_syntax.add(jmi_syntax_json);
        JMenuItem jmi_syntax_none = new JMenuItem("None");
        jmi_syntax_none.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent arg0) {
                actionTextEditorSyntaxChange(se_response, TextEditorSyntax.DEFAULT);
            }
        });
        jm_syntax.add(jmi_syntax_none);
       
        popupMenu.add(jm_syntax);
       
        // Attach popup menu
        if (se_response.getEditorComponent() instanceof JEditorPane) {
            se_response.getEditorComponent().addMouseListener(new MouseAdapter() {
                @Override
                public void mousePressed(MouseEvent e) {
                    showPopup(e);
                }

                @Override
                public void mouseReleased(MouseEvent e) {
                    showPopup(e);
                }
                private void showPopup(final MouseEvent e) {
                    if("".equals(se_response.getText().trim())){
                        // No response body
                        return;
                    }
                    if (e.isPopupTrigger()) {
                        popupMenu.show(e.getComponent(), e.getX(), e.getY());
                    }
                }
            });
        }
        JPanel jp_body = new JPanel();
        jp_body.setLayout(new GridLayout(1,1));
        se_response.setEditable(false);
        jp_body.add(se_response.getEditorView());
        JPanel jp_body_encp = new JPanel();
        jp_body_encp.setBorder(BorderFactory.createEmptyBorder());
        jp_body_encp.setLayout(new GridLayout(1, 1));
        jp_body_encp.add(jp_body);
        jtp.addTab("Body", jp_body_encp);
       
        // Test result
        JPanel jp_test_result = new JPanel();
        jp_test_result.setLayout(new GridLayout(1, 1));
        jp_test_result.add(jp_testResultPanel);
        jtp.addTab("Test Result", jp_test_result);
       
        return jtp;
    }
   
    private JPanel initUIRequest(){
        JPanel jp = new JPanel();
        jp.setBorder(BorderFactory.createEmptyBorder(
                BORDER_WIDTH, BORDER_WIDTH, BORDER_WIDTH, BORDER_WIDTH));
        jp.setLayout(new BorderLayout(BORDER_WIDTH, BORDER_WIDTH));
       
        // North
        JPanel jp_north = new JPanel();
        jp_north.setLayout(new BorderLayout(BORDER_WIDTH, 0));
        jl_url.setLabelFor(jcb_url);
        jl_url.setDisplayedMnemonic('u');
        jp_north.add(jl_url, BorderLayout.WEST);
       
        jcb_url.setToolTipText("URL");
        jcb_url.setEditable(true);
        jcb_url.addActionListener(new java.awt.event.ActionListener() {
            @Override
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                jcb_urlActionPerformed(evt);
            }
        });
        jcb_url.getEditor().addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                fromKeyboard = true;
            }
        });
        jcb_url.getEditor().getEditorComponent().addFocusListener(new FocusAdapter() {
            @Override
            public void focusGained(FocusEvent e) {
                ((JTextField) jcb_url.getEditor().getEditorComponent()).selectAll();
            }
        });
        // AutoCompleteDecorator.decorate(jcb_url);
        AutoCompletion ac = new AutoCompletion(jcb_url);
        ac.setStrict(false);
        jp_north.add(jcb_url, BorderLayout.CENTER);
        jb_request = new JButton(icon_go);
        jb_request.setToolTipText("Go!");
        jb_request.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent event) {
                jb_requestActionPerformed();
            }
        });
        jp_north.add(jb_request, BorderLayout.EAST);
        jp.add(jp_north, BorderLayout.NORTH);
       
        // Center
        jp.add(initJTPRequest(), BorderLayout.CENTER);
       
        jp.setBorder(BorderFactory.createTitledBorder(null, "HTTP Request", TitledBorder.CENTER, TitledBorder.DEFAULT_POSITION));
        return jp;
    }
   
    private JPanel initUIResponse(){
        JPanel jp = new JPanel();
        // Set top as 0:
        jp.setBorder(BorderFactory.createEmptyBorder(
                0, BORDER_WIDTH, BORDER_WIDTH, BORDER_WIDTH));
        jp.setLayout(new BorderLayout(BORDER_WIDTH, BORDER_WIDTH));
       
        // Header Tab: Status Line Header
        JPanel jp_status = new JPanel();
        jp_status.setLayout(new BorderLayout(BORDER_WIDTH, BORDER_WIDTH));
        JLabel jl_res_statusLine = new JLabel("Status: ");
        jp_status.add(jl_res_statusLine, BorderLayout.WEST);
        jtf_res_status.setColumns(35);
        jtf_res_status.setEditable(false);
        jp_status.add(jtf_res_status, BorderLayout.CENTER);
       
        jp.add(jp_status, BorderLayout.NORTH);
       
        // Center having tabs
        jp.add(initJTPResponse(), BorderLayout.CENTER);
       
        jp.setBorder(BorderFactory.createTitledBorder(null, "HTTP Response", TitledBorder.CENTER, TitledBorder.DEFAULT_POSITION));
        return jp;
    }
   
    private JPanel initUIStatusBar(){
        JPanel jp = new JPanel();
        jp.setBorder(BorderFactory.createBevelBorder(1));
        jp.setLayout(new GridLayout(1, 2));
        jl_status.setFont(UIUtil.FONT_DIALOG_12_PLAIN);
        jp.add(jl_status);
        JPanel jp_south_jcb = new JPanel();
        jp_south_jcb.setLayout(new FlowLayout(FlowLayout.RIGHT));
        Dimension d = jpb_status.getPreferredSize();
        d.height = d.height - 2;
        jpb_status.setPreferredSize(d);
        jpb_status.setIndeterminate(true);
        jpb_status.setVisible(false);
        jp_south_jcb.add(jpb_status);
        jp.add(jp_south_jcb);
        return jp;
    }
   
    private void init(){
        // Initialize the messageDialog
        messageDialog = new MessageDialog(rest_ui.getFrame());
       
        // Initialize parameter dialog
        ParameterView pv = new ParameterView(){
            @Override
            public void setParameter(final String params) {
                se_req_body.setText(params);
            }
           
        };
        jd_req_paramDialog = new ParameterDialog(rest_ui, pv);
       
        // Initialize jd_body_content_type
        jd_body_content_type = new BodyContentTypeDialog(rest_ui.getFrame());
        jd_body_content_type.addContentTypeCharSetChangeListener(new ContentTypeCharSetChangeListener() {
            @Override
            public void changed(String contentType, String charSet) {
                jtf_body_content_type.setText(Util.getFormattedContentType(contentType, charSet));
            }
        });
       
        // Set the font of ScriptEditors:
        String fontName = Implementation.of(IGlobalOptions.class).getProperty("font.options.font");
        String fontSizeStr = Implementation.of(IGlobalOptions.class).getProperty("font.options.fontSize");
        int fontSize = 12; // Default font size is 12
        if(fontSizeStr != null){
            try{
                fontSize = Integer.parseInt(fontSizeStr);
            }
            catch(NumberFormatException ex){
                LOG.log(Level.WARNING, "Font size property is not a number: {0}", fontSizeStr);
            }
        }
        if(fontName != null){
            Font f = new Font(fontName, Font.PLAIN, fontSize);
            se_req_body.getEditorComponent().setFont(f);
            se_response.getEditorComponent().setFont(f);
        }
       
        this.setLayout(new BorderLayout());
       
        // Adding the Center portion
        JSplitPane jsp_main = new JSplitPane(JSplitPane.VERTICAL_SPLIT);
        jsp_main.setDividerSize(5);
        jsp_main.add(initUIRequest());
        jsp_main.add(initUIResponse());
        this.add(jsp_main, BorderLayout.CENTER);
       
        // Now the South portion
        this.add(initUIStatusBar(), BorderLayout.SOUTH);
    }
   
    void showSessionFrame(){
        if(!sessionFrame.isVisible()){
            sessionFrame.setVisible(true);
        }
    }
   
    void setUIToLastRequestResponse(){
        if(lastRequest != null && lastResponse != null){
            setUIFromRequest(lastRequest);
            setUIFromResponse(lastResponse);
        }
    }
   
    Response getResponseFromUI(){
        ResponseBean response = new ResponseBean();
        response.setResponseBody(unindentedResponseBody);
        String statusLine = jtf_res_status.getText();
        response.setStatusLine(statusLine);
        response.setStatusCode(Util.getStatusCodeFromStatusLine(statusLine));
        String[][] headers = ((ResponseHeaderTableModel)jt_res_headers.getModel()).getHeaders();
        for(int i=0; i<headers.length; i++){
            response.addHeader(headers[i][0], headers[i][1]);
        }
        response.setTestResult(jp_testResultPanel.getTestResult());
        return response;
    }
   
    public Request getRequestFromUI(){
        correctRequestURL();
        /*List<String> errors = validateForRequest();
        if(errors.size()!=0){
            String errStr = Util.getHTMLListFromList(errors);
            JOptionPane.showMessageDialog(rest_ui.getFrame(),
                errStr,
                "Validation error",
                JOptionPane.ERROR_MESSAGE);
            return null;
        }*/
       
        RequestBean request = new RequestBean();
        boolean authEnabled = false;
       
        if(jcb_auth_basic.isSelected()){
            request.addAuthMethod(HTTPAuthMethod.BASIC);
            authEnabled = true;
        }
        if(jcb_auth_digest.isSelected()){
            request.addAuthMethod(HTTPAuthMethod.DIGEST);
            authEnabled = true;
        }
       
        if(authEnabled){
            // Pass the credentials
            String uid = jtf_auth_username.getText();
            char[] pwd = jpf_auth_password.getPassword();
           
            String realm = jtf_auth_realm.getText();
            String host = jtf_auth_host.getText();
            boolean preemptive = jcb_auth_preemptive.isSelected();
           
            request.setAuthPreemptive(preemptive);
            request.setAuthUsername(uid);
            request.setAuthPassword(pwd);
            request.setAuthRealm(realm);
            request.setAuthHost(host);
        }
       
        String url = (String)jcb_url.getSelectedItem();
        try{
            request.setUrl(new URL(url));
        }
        catch(MalformedURLException ex){
            // URL is left null!
        }
        if(jrb_req_get.isSelected()){
            request.setMethod(HTTPMethod.GET);
        }
        else if(jrb_req_head.isSelected()){
            request.setMethod(HTTPMethod.HEAD);
        }
        else if(jrb_req_post.isSelected()){
            request.setMethod(HTTPMethod.POST);
        }
        else if(jrb_req_put.isSelected()){
            request.setMethod(HTTPMethod.PUT);
        }
        else if(jrb_req_delete.isSelected()){
            request.setMethod(HTTPMethod.DELETE);
        }
        else if(jrb_req_options.isSelected()){
            request.setMethod(HTTPMethod.OPTIONS);
        }
        else if(jrb_req_trace.isSelected()){
            request.setMethod(HTTPMethod.TRACE);
        }
       
        // Get request headers
        Object[][] header_data = jp_2col_req_headers.getTableModel().getData();
        if(header_data.length > 0){
            for(int i=0; i<header_data.length; i++){
                String key = (String)header_data[i][0];
                String value = (String)header_data[i][1];
                request.addHeader(key, value);
            }
        }
       
        // EntityEnclosing method specific
        if(jrb_req_post.isSelected() || jrb_req_put.isSelected()){
            // Get request body
            String req_body = se_req_body.getText();
            if(!StringUtil.isStrEmpty(req_body)){
                String req_content_type = jd_body_content_type.getContentType();
                String req_char_set = jd_body_content_type.getCharSet();
                ReqEntityBean body = new ReqEntityBean(req_body,
                        req_content_type,
                        req_char_set);
                request.setBody(body);
            }
        }
       
        // SSL specific
        request.setSslTrustStore(jtf_ssl_truststore_file.getText());
        request.setSslTrustStorePassword(jpf_ssl_truststore_pwd.getPassword());
        request.setSslHostNameVerifier((SSLHostnameVerifier)jcb_ssl_hostname_verifier.getSelectedItem());
       
        // HTTP version
        request.setHttpVersion((HTTPVersion)jcb_http_version.getSelectedItem());

        // Follow redirect
        request.setFollwoRedirect(jcb_followRedirects.isSelected());
       
        // Test script specific
        String testScript = se_test_script.getText();
        testScript = testScript == null || testScript.trim().equals("")?
            null: testScript.trim();
        request.setTestScript(testScript);
        return request;
    }

    private void jb_requestActionPerformed() {
        if(jb_request.getIcon() == icon_go){
            final Request request = getRequestFromUI();
            List<String> errors = validateRequest(request);
            if(errors.isEmpty()){
                clearUIResponse();
                final RequestExecuter executer = Implementation.of(RequestExecuter.class);
                // Execute the request:
                requestThread = new Thread(){
                    @Override
                    public void run(){
                        executer.execute(request, view);
                    }

                    @Override
                    public void interrupt(){
                        executer.abortExecution();
                        super.interrupt();
                    }
                };
                requestThread.start();
            }
            else{
                String errStr = Util.getHTMLListFromList(errors);
                JOptionPane.showMessageDialog(rest_ui.getFrame(),
                    errStr,
                    "Validation error",
                    JOptionPane.ERROR_MESSAGE);
            }
        }
        else if(jb_request.getIcon() == icon_stop){
            requestThread.interrupt();
            jb_request.setIcon(icon_go);
        }
    }                                         

    @Override
    public void doStart(Request request){
        lastRequest = request;
       
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                jpb_status.setVisible(true);
                // jb_request.setEnabled(false);
                jb_request.setIcon(icon_stop);
                jb_request.setToolTipText("Stop!");

                // Update status message
                setStatusMessage("Processing request...");
            }
        });
    }
   
    @Override
    public void doResponse(final Response response){
        lastResponse = response;
   
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                // Update the UI:
                setUIFromResponse(response);

                // Update status message
                setStatusMessage("Response received in: " + response.getExecutionTime() + " ms");

                // Update Session View
                if(sessionFrame.isVisible()){
                    sessionFrame.getSessionView().add(lastRequest, lastResponse);
                }
            }
        });
    }
   
    @Override
    public void doCancelled(){
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                setStatusMessage("Request cancelled!");
            }
        });
    }
   
    @Override
    public void doEnd(){
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                jpb_status.setVisible(false);
                // jb_request.setEnabled(true);
                jb_request.setIcon(icon_go);
                jb_request.setToolTipText("Go!");
            }
        });
    }
   
    @Override
    public void doError(final String error){
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                showError(error);
                setStatusMessage("An error occurred during request.");
            }
        });
       
    }
   
    public void showError(final String error){
        messageDialog.showError(error);
    }
   
    public void showMessage(final String title, final String message){
        messageDialog.showMessage(title, message);
    }
   
    void clearUIResponse(){
        unindentedResponseBody = null;
        jtf_res_status.setText("");
        se_response.setText("");
        ResponseHeaderTableModel model = (ResponseHeaderTableModel)jt_res_headers.getModel();
        model.setHeaders(null);
        jp_testResultPanel.clear();
    }
   
    private void jcb_urlActionPerformed(final ActionEvent event){
        if("comboBoxChanged".equals(event.getActionCommand())){
            return;
        }
        final Object item = jcb_url.getSelectedItem();
        final int count = jcb_url.getItemCount();
        final LinkedList l = new LinkedList();
        for(int i=0; i<count; i++){
            l.add(jcb_url.getItemAt(i));
        }
        if(l.contains(item)){ // Item already present
            // Remove and add to bring it to the top
            // l.remove(item);
            // l.addFirst(item);
            // System.out.println("Removing and inserting at top");
            jcb_url.removeItem(item);
            jcb_url.insertItemAt(item, 0);
        }
        else{ // Add new item
            if(((String)item).trim().length() != 0 ) {
                // The total number of items should not exceed 20
                if(count > 19){
                    // Remove last item to give place
                    // to new one
                    //l.removeLast();
                    jcb_url.removeItemAt(count - 1);
                }
                //l.addFirst(item);
                jcb_url.insertItemAt(item, 0);
            }
        }
        // make the selected item is the item we want
        jcb_url.setSelectedItem(item);
        // Use this to trigger request action on pressing Enter:
        if (fromKeyboard) {
            fromKeyboard = false;
            jb_requestActionPerformed();
        }
    }
   
    private void auth_enableActionPerformed(final ActionEvent event){
        if(jcb_auth_basic.isSelected() || jcb_auth_digest.isSelected()){
            setUIReqAuthEnabled(true);
        }
        else{
            setUIReqAuthEnabled(false);
        }
    }
   
    private void setUIReqAuthEnabled(final boolean boo){
        jcb_auth_preemptive.setEnabled(boo);
        jtf_auth_host.setEnabled(boo);
        jtf_auth_realm.setEnabled(boo);
        jtf_auth_username.setEnabled(boo);
        jpf_auth_password.setEnabled(boo);

        // Disable/enable labels:
        jl_auth_host.setEnabled(boo);
        jl_auth_realm.setEnabled(boo);
        jl_auth_username.setEnabled(boo);
        jl_auth_password.setEnabled(boo);
    }
   
    private void jb_body_fileActionPerformed(ActionEvent event){
        if(!canSetReqBodyText()){
            return;
        }
        File f = rest_ui.getOpenFile(FileChooserType.OPEN_REQUEST_BODY);
        if(f == null){ // Pressed cancel?
            return;
        }
        if(!f.canRead()){
            JOptionPane.showMessageDialog(rest_ui.getFrame(),
                    "File not readable: " + f.getAbsolutePath(),
                    "IO Error",
                    JOptionPane.ERROR_MESSAGE);
            return;
        }
        // Determine the MIME type and set parameter
        String contentType = FileUtil.getMimeType(f);
        String charset = null;
        if(XMLUtil.XML_MIME.equals(contentType)){
            try{
                charset = XMLUtil.getDocumentCharset(f);
            }
            catch(IOException ex){
                // Do nothing!
            }
            catch(XMLException ex){
                // Do nothing!
            }
        }
        String oldContentType = jd_body_content_type.getContentType();
        String oldCharset = jd_body_content_type.getCharSet();
        if(!oldContentType.equals(contentType)){
            int contentTypeYesNo = JOptionPane.showConfirmDialog(view,
                    "Change ContentType To: " + contentType + "?",
                    "Change ContentType?", JOptionPane.YES_NO_OPTION);
            if(contentTypeYesNo == JOptionPane.YES_OPTION){
                jd_body_content_type.setContentType(contentType);
                if(charset != null){ // is XML file
                    jd_body_content_type.setCharSet(charset);
                }
            }
        }
        // Only the charset has changed:
        else if((charset != null) && (!oldCharset.equals(charset))){
            int charsetYesNo = JOptionPane.showConfirmDialog(view,
                    "Change Charset To: " + charset + "?",
                    "Change Charset?", JOptionPane.YES_NO_OPTION);
            if(charsetYesNo == JOptionPane.YES_OPTION){
                jd_body_content_type.setCharSet(charset);
            }
        }
        // Get text from file and set
        try{
            String body = FileUtil.getContentAsString(f, Charsets.UTF_8);
            se_req_body.setText(body);
            se_req_body.setCaretPosition(0);
        }
        catch(IOException ex){
            JOptionPane.showMessageDialog(rest_ui.getFrame(),
                    "IO Error: " + ex.getMessage(),
                    "IO Error",
                    JOptionPane.ERROR_MESSAGE);
            jd_body_content_type.setContentType(oldContentType);
            jd_body_content_type.setCharSet(oldCharset);
        }
    }
   
    private void jb_body_paramActionPerformed(ActionEvent event){
        if(!canSetReqBodyText()){
            return;
        }
        checkAndSetParameterContentType();
        jd_req_paramDialog.setLocationRelativeTo(rest_ui.getFrame());
        jd_req_paramDialog.setVisible(true);
    }
   
    private boolean canSetReqBodyText(){
        if(StringUtil.isStrEmpty(se_req_body.getText())){
            return true;
        }
        else{
            int response = JOptionPane.showConfirmDialog(rest_ui.getFrame(),
                    "Body text exists. Erase?",
                    "Erase?",
                    JOptionPane.YES_NO_OPTION);
            if(response == JOptionPane.YES_OPTION){
                return true;
            }
        }
        return false;
    }
   
   
    private void checkAndSetParameterContentType(){
        if(!jd_body_content_type.getContentType().equals(BodyContentTypeDialog.PARAM_CONTENT_TYPE)
                || !jd_body_content_type.getCharSet().equals(BodyContentTypeDialog.PARAM_CHARSET)){
            int status = JOptionPane.showConfirmDialog(rest_ui.getFrame(),
                    "<html>For parameter the Content-type and Charset needs <br>" +
                    "to be `" + BodyContentTypeDialog.PARAM_CONTENT_TYPE +
                    "' and `"+
                    BodyContentTypeDialog.PARAM_CHARSET +
                    "' respectively.<br>"+
                    "Do you want to set this option?</html>",
                    "Parameter Content-type and Charset",
                    JOptionPane.YES_NO_OPTION);
            if(status == JOptionPane.YES_OPTION){
                jd_body_content_type.setContentType(BodyContentTypeDialog.PARAM_CONTENT_TYPE);
                jd_body_content_type.setCharSet(BodyContentTypeDialog.PARAM_CHARSET);
            }
        }
    }
   
    private void setUIReqBodyEnabled(final boolean boo){
        se_req_body.getEditorComponent().setEnabled(boo);
        jb_body_content_type.setEnabled(boo);
        jb_body_file.setEnabled(boo);
        jb_body_params.setEnabled(boo);
    }
   
  
    // Checks if URL starts with http:// or https://
    // If not, appends http:// to the hostname
    // This is just a UI convenience method.
    private void correctRequestURL(){
        String str = (String)jcb_url.getSelectedItem();
        if(StringUtil.isStrEmpty(str)){
            return;
        }
        else{
            String t = str.toLowerCase();
            if(!(t.startsWith("http://")
                    || t.startsWith("https://")
                    || t.matches("^[a-z]+://.*"))){
                str = "http://" + str;
                jcb_url.setSelectedItem(str);
            }
        }
    }
   
    private List<String> validateRequest(Request request){
        List<String> errors = new ArrayList<String>();

        // Check URL
        if(request.getUrl() == null){
            errors.add("URL is invalid.");
        }
       
        // Auth check
        if(request.getAuthMethods().size() > 0){
            if(StringUtil.isStrEmpty(request.getAuthUsername())){
                errors.add("Username is empty.");
            }
            if(StringUtil.isStrEmpty(new String(request.getAuthPassword()))){
                errors.add("Password is empty.");
            }
        }
       
        // Req Entity check
        final HTTPMethod METHOD = request.getMethod();
        if(METHOD == HTTPMethod.POST || METHOD == HTTPMethod.PUT){
            // Get request body
            ReqEntity reBean = request.getBody();
            if(reBean != null){
                String req_body = reBean.getBody();
                if(!StringUtil.isStrEmpty(req_body)){
                    String req_content_type = reBean.getContentType();
                    String req_char_set = reBean.getCharSet();
                    if(StringUtil.isStrEmpty(req_content_type)
                            || StringUtil.isStrEmpty(req_char_set)){
                        errors.add("Body content is set, but `Content-type' and/or `Char-set' not set.");
                    }
                }
            }
        }
        return errors;
    }
   
    void clearUIRequest(){
        // URL
        jcb_url.setSelectedItem(null);
       
        // Method
        jrb_req_get.setSelected(true);
       
        // Headers
        jp_2col_req_headers.getTableModel().setData(CollectionsUtil.EMPTY_MULTI_VALUE_MAP);
       
        // Body
        jd_body_content_type.setContentType(BodyContentTypeDialog.DEFAULT_CONTENT_TYPE);
        jd_body_content_type.setCharSet(BodyContentTypeDialog.DEFAULT_CHARSET);
        se_req_body.setText("");
        setUIReqBodyEnabled(false);
       
        // Auth
        jcb_auth_basic.setSelected(false);
        jcb_auth_digest.setSelected(false);
        jcb_auth_preemptive.setSelected(true);
        jtf_auth_host.setText("");
        jtf_auth_realm.setText("");
        jtf_auth_username.setText("");
        jpf_auth_password.setText("");
        setUIReqAuthEnabled(false);
       
        // SSL
        jtf_ssl_truststore_file.setText("");
        jpf_ssl_truststore_pwd.setText("");
        jcb_ssl_hostname_verifier.setSelectedIndex(0);
       
        // HTTP version
        jcb_http_version.setSelectedItem(HTTPVersion.getDefault());
       
        // Script
        se_test_script.setText("");
    }
   
    void setUIFromResponse(final Response response){
        // Clear first
        clearUIResponse();

        // Response status line
        jtf_res_status.setText(response.getStatusLine());

        // Response header
        resHeaderTableModel.setHeaders(response.getHeaders());

        // Response body
        //// Set the unindentedResponseBody:
        unindentedResponseBody = response.getResponseBody();
        IGlobalOptions options = Implementation.of(IGlobalOptions.class);
        String indentStr = options.getProperty("response.body.indent");
        boolean indent = indentStr==null? false: (indentStr.equals("true")? true: false);
        if(indent){
            boolean isXml = false;
            boolean isJson = false;
            MultiValueMap<String, String> headers = response.getHeaders();
            for(String key: headers.keySet()){
                if("content-type".equalsIgnoreCase(key)){
                    for(String v: headers.get(key)) {
                        final String contentType = Util.getMimeFromContentType(v);
                        if(contentType.startsWith("application/xml")
                                || contentType.startsWith("text/xml")
                                || contentType.endsWith("+xml")){
                            isXml = true;
                        }
                        else if(contentType.startsWith("application/json")){
                            isJson = true;
                        }
                        break;
                    }
                }
            }
            final String responseBody = response.getResponseBody();
            if(isXml){
                try{
                    String indentedResponseBody = XMLUtil.indentXML(responseBody);
                    se_response.setText(indentedResponseBody);
                }
                catch(IOException ex){
                    setStatusMessage("XML indentation failed.");
                    LOG.warning(ex.getMessage());
                    se_response.setText(responseBody);
                }
                catch(XMLException ex){
                    setStatusMessage("XML indentation failed.");
                    LOG.warning(ex.getMessage());
                    se_response.setText(responseBody);
                }
            }
            else if(isJson){
                try{
                    String indentedResponseBody = JSONUtil.indentJSON(responseBody);
                    se_response.setText(indentedResponseBody);
                }
                catch(JSONUtil.JSONParseException ex){
                    setStatusMessage("JSON indentation failed.");
                    LOG.warning(ex.getMessage());
                    se_response.setText(responseBody);
                }
            }
            else{
                setStatusMessage("Response body neither XML nor JSON. No indentation.");
                se_response.setText(responseBody);
            }
        }
        else{
            se_response.setText(response.getResponseBody());
        }
        se_response.setCaretPosition(0);

        // Response test result
        jp_testResultPanel.setTestResult(response.getTestResult());
    }
   
    void setUIFromRequest(final Request request){
        // Clear first
        clearUIRequest();

        // URL
        jcb_url.setSelectedItem(request.getUrl().toString());

        // Method
        final HTTPMethod reqMethod = request.getMethod();
        switch(reqMethod){
            case GET:
                jrb_req_get.setSelected(true);
                break;
            case POST:
                jrb_req_post.setSelected(true);
                break;
            case PUT:
                jrb_req_put.setSelected(true);
                break;
            case DELETE:
                jrb_req_delete.setSelected(true);
                break;
            case HEAD:
                jrb_req_head.setSelected(true);
                break;
            case OPTIONS:
                jrb_req_options.setSelected(true);
                break;
            case TRACE:
                jrb_req_trace.setSelected(true);
                break;
        }

        // Headers
        MultiValueMap<String, String> headers = request.getHeaders();
        jp_2col_req_headers.getTableModel().setData(headers);

        // Body
        ReqEntity body = request.getBody();
        if(body != null){
            if(jrb_req_post.isSelected() || jrb_req_put.isSelected()){
                setUIReqBodyEnabled(true);
            }
            jd_body_content_type.setContentType(body.getContentType());
            jd_body_content_type.setCharSet(body.getCharSet());
            se_req_body.setText(body.getBody());
            se_req_body.setCaretPosition(0);
        }

        // Authentication
        List<HTTPAuthMethod> authMethods = request.getAuthMethods();
        if(authMethods.size() > 0){
            setUIReqAuthEnabled(true);
        }
        for(HTTPAuthMethod authMethod: authMethods){
            switch(authMethod){
                case BASIC:
                    jcb_auth_basic.setSelected(true);
                    break;
                case DIGEST:
                    jcb_auth_digest.setSelected(true);
                    break;
            }
        }
        jcb_auth_preemptive.setSelected(request.isAuthPreemptive());
        jtf_auth_host.setText(StringUtil.getNullStrIfNull(request.getAuthHost()));
        jtf_auth_realm.setText(StringUtil.getNullStrIfNull(request.getAuthRealm()));
        jtf_auth_username.setText(StringUtil.getNullStrIfNull(request.getAuthUsername()));
        if(request.getAuthPassword() != null){
            jpf_auth_password.setText(new String(request.getAuthPassword()));
        }

        // SSL
        String sslTruststore = request.getSslTrustStore();
        char[] sslTruststorePassword = request.getSslTrustStorePassword();
        if(sslTruststore != null){
            jtf_ssl_truststore_file.setText(sslTruststore);
        }
        if(sslTruststorePassword != null){
            jpf_ssl_truststore_pwd.setText(new String(sslTruststorePassword));
        }
        SSLHostnameVerifier sslHostnameVerifier = request.getSslHostNameVerifier();
        if(sslHostnameVerifier != null){
            jcb_ssl_hostname_verifier.setSelectedItem(sslHostnameVerifier);
        }

        // HTTP Version
        if(request.getHttpVersion() == HTTPVersion.HTTP_1_1){
            jcb_http_version.setSelectedItem(HTTPVersion.HTTP_1_1);
        }
        else if(request.getHttpVersion() == HTTPVersion.HTTP_1_0){
            jcb_http_version.setSelectedItem(HTTPVersion.HTTP_1_0);
        }

        // Follow redirect
        jcb_followRedirects.setSelected(request.isFollowRedirect());

        // Test script
        se_test_script.setText(request.getTestScript()==null?"":request.getTestScript());
        se_test_script.setCaretPosition(0);
    }
   
    private Calendar statusLastUpdated;
   
    public void setStatusMessage(final String msg){
        jl_status.setText(" " + msg);
        statusLastUpdated = Calendar.getInstance();
    }
   
    public Request getLastRequest() {
        return lastRequest;
    }

    public Response getLastResponse() {
        return lastResponse;
    }
   
    public Font getTextAreaFont(){
        return se_req_body.getEditorComponent().getFont();
    }
   
    public void setTextAreaFont(final Font f){
        se_req_body.getEditorComponent().setFont(f);
        se_response.getEditorComponent().setFont(f);
    }
   
}
TOP

Related Classes of org.wiztools.restclient.ui.RESTView

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.