/**
  * Attemps to parse the specified url using {@link FileURL#getFileURL(String)} and returns <code>
  * true</code> if it succeeded, <code>false</code> if it threw a <code>MalformedURLException
  * </code>.
  *
  * @param url the URL to try and parse
  * @return <code>true</code> if the URL could be parsed, <code>false</code> if a <code>
  *     MalformedURLException</code> was thrown
  */
 protected boolean canParse(String url) {
   try {
     FileURL.getFileURL(url);
     return true;
   } catch (MalformedURLException e) {
     return false;
   }
 }
  /**
   * Ensure that non URL-safe characters in login and password parts are properly handled, both when
   * parsing and representing URLs as string.
   *
   * @throws MalformedURLException should not happen
   */
  @Test
  public void testCredentialsURLEncoding() throws MalformedURLException {
    FileURL url = getRootURL();

    String urlDecodedString = ":@&=+$,/?t%#[]";
    String urlEncodedString = "%3A%40%26%3D%2B%24%2C%2F%3Ft%25%23%5B%5D";

    url.setCredentials(new Credentials(urlDecodedString, urlDecodedString));
    String urlRep = url.getScheme() + "://" + urlEncodedString + ":" + urlEncodedString + "@";
    assert urlRep.equals(url.toString(true, false));

    url = FileURL.getFileURL(urlRep);
    Credentials credentials = url.getCredentials();
    assert credentials.getLogin().equals(urlDecodedString);
    assert credentials.getPassword().equals(urlDecodedString);
  }
  /**
   * Creates a URL from the given parts, ensuring that parsing it yields the given parts, and
   * returns it.
   *
   * @param login login part, may be <code>null</code>
   * @param password password part, may be <code>null</code>
   * @param host host part, may be <code>null</code>
   * @param port port part, <code>-1</code> for none
   * @param path path part
   * @param query query part, may be <code>null</code>
   * @return a URL corresponding to the given parts
   * @throws MalformedURLException if the URL cannot be parsed
   */
  protected FileURL getURL(
      String login, String password, String host, int port, String path, String query)
      throws MalformedURLException {
    String scheme = getScheme();
    StringBuffer sb = new StringBuffer(scheme + "://");

    if (host != null) {
      if (login != null) {
        sb.append(login);

        if (password != null) {
          sb.append(':');
          sb.append(password);
        }

        sb.append('@');
      }

      sb.append(host);

      if (port != -1) {
        sb.append(':');
        sb.append(port);
      }
    }

    path = getSchemePath(path);
    sb.append(path);

    if (query != null) {
      sb.append('?');
      sb.append(query);
    }

    // Assert that each of the url's parts match

    FileURL url = FileURL.getFileURL(sb.toString());

    assert scheme.equals(url.getScheme());

    if (host != null) {
      if (login != null) {
        assert login.equals(url.getLogin());
        assert url.containsCredentials();

        if (password != null) assert password.equals(url.getPassword());

        assert new Credentials(login, password).equals(url.getCredentials(), true);
      }

      assert host.equals(url.getHost());
      assert port == url.getPort();
    }

    if (query != null && !isQueryParsed()) {
      assert url.getQuery() == null;
      path = path + "?" + query;
    } else if (query == null) assert url.getQuery() == null;
    else assert query.equals(url.getQuery());

    assertPathEquals(path, url);

    // Test the URL's string representation
    assert url.equals(FileURL.getFileURL(url.toString(true, false)));
    assert url.equals(FileURL.getFileURL(url.toString(false, false)), false, false);

    return url;
  }
 /**
  * Returns the simplest FileURL instance possible using the scheme returned by {@link
  * #getScheme()}, containing only the scheme and '/' as a path. For instance, if <code>http</code>
  * is the current scheme, a FileURL with <code>http:///</code> as a string representation will be
  * returned.
  *
  * @return a 'root' FileURL instance with the scheme returned by {@link # getScheme ()}
  * @throws MalformedURLException should never happen
  */
 protected FileURL getRootURL() throws MalformedURLException {
   return FileURL.getFileURL(getScheme() + ":///");
 }
 // - Initialisation --------------------------------------------------------
 // -------------------------------------------------------------------------
 public BookmarkRoot() throws IOException {
   this(FileURL.getFileURL(BookmarkProtocolProvider.BOOKMARK + "://"));
 }