private void processResponse(RubyValue res) {
    if (res != null && res != RubyConstant.QNIL && res instanceof RubyHash) {
      RubyHash resHash = (RubyHash) res;
      RubyValue resBody = null;

      RubyArray arKeys = resHash.keys();
      RubyArray arValues = resHash.values();
      for (int i = 0; i < arKeys.size(); i++) {
        String strKey = arKeys.get(i).toString();
        if (strKey.equals("request-body")) resBody = arValues.get(i);
        else if (strKey.equals("status")) responseCode = arValues.get(i).toInt();
        else if (strKey.equals("message")) responseMsg = arValues.get(i).toString();
        else resHeaders.addProperty(strKey, arValues.get(i).toString());
      }
      String strBody = "";

      if (resBody != null && resBody != RubyConstant.QNIL)
        strBody = resBody.toRubyString().toString();

      if (!RHOCONF().getBool("log_skip_post")) LOG.TRACE(strBody);

      try {
        responseData = new ByteArrayInputStream(strBody.getBytes("UTF-8"));
      } catch (java.io.UnsupportedEncodingException exc) {
        LOG.ERROR("Error getting utf-8 body :", exc);
      }

      if (responseData != null)
        contentLength = Integer.parseInt(resHeaders.getPropertyIgnoreCase("Content-Length"));
    }
  }
 public String getHeaderField(int index) throws IOException {
   LOG.TRACE("getHeaderField: " + index);
   processRequest();
   if (index >= resHeaders.size()) {
     return null;
   }
   return resHeaders.getValueAt(index);
 }
 public String getEncoding() {
   LOG.TRACE("getEncloding");
   try {
     return getHeaderField("content-encoding");
   } catch (IOException x) {
     return null;
   }
 }
 public String getType() {
   LOG.TRACE("getType");
   try {
     return getHeaderField("content-type");
   } catch (IOException x) {
     return null;
   }
 }
 public long getLength() {
   LOG.TRACE("getLength: " + contentLength);
   try {
     processRequest();
   } catch (IOException ioe) {
     // Fall through to return -1 for length
   }
   return contentLength;
 }
  protected boolean httpServeFile(String strContType) throws IOException {
    String strPath = uri.getPath();
    // if ( !strPath.startsWith("/apps") )
    //	strPath = "/apps" + strPath;

    LOG.TRACE("httpServeFile: " + strPath);

    if (!isDbFilesPath(strPath)) {
      if (strContType.equals("application/javascript")) {
        responseData = RhoRuby.loadFile(strPath);
        if (responseData == null) {
          String str = "";
          responseData = new ByteArrayInputStream(str.getBytes());
        }
      } else responseData = RhoRuby.loadFile(strPath);
    } else {
      if (strPath.startsWith("/apps/app/db/db-files"))
        strPath = strPath.substring(9); // remove /apps/app
      else strPath = strPath.substring(5); // remove /apps
    }

    if (responseData == null) {

      SimpleFile file = null;
      try {
        file = RhoClassFactory.createFile();
        String strFileName = strPath;
        //				if ( strFileName.startsWith("/apps") )
        //					strFileName = strPath.substring(5);

        file.open(strFileName, true, true);
        responseData = file.getInputStream();
        if (responseData != null) {
          contentLength = (int) file.length();
        }
        m_file = file;
      } catch (Exception exc) {
        if (file != null) file.close();
      }
    } else {
      if (responseData != null) {
        contentLength = responseData.available();
      }
    }

    if (responseData == null) return false;

    if (strContType.length() > 0) resHeaders.addProperty("Content-Type", strContType);

    resHeaders.addProperty("Content-Length", Integer.toString(contentLength));

    // resHeaders.addProperty("Date",getLocalHttpTimeString());
    // resHeaders.addProperty("Cache-control", "public, max-age=3600" );
    // resHeaders.addProperty("Expires", "Thu, 01 Dec 2010 16:00:00 GMT" );

    return true;
  }
 public int getHeaderFieldInt(String name, int def) throws IOException {
   LOG.TRACE("getHeaderFieldInt: " + name);
   processRequest();
   try {
     return Integer.parseInt(getHeaderField(name));
   } catch (IllegalArgumentException iae) {
     // fall through
   } catch (NullPointerException npe) {
     // fall through
   }
   return def;
 }
 public long getHeaderFieldDate(String name, long def) throws IOException {
   LOG.TRACE("getHeaderFieldDate: " + name);
   processRequest();
   try {
     return DateTimeTokenizer.parse(getHeaderField(name));
   } catch (NumberFormatException nfe) {
     // fall through
   } catch (IllegalArgumentException iae) {
     // fall through
   } catch (NullPointerException npe) {
     // fall through
   }
   return def;
 }
 public String getFile() {
   LOG.TRACE("getFile");
   if (uri != null) {
     String path = uri.getPath();
     if (path != null) {
       int s0 = path.lastIndexOf('/');
       int s1 = path.lastIndexOf('\\');
       if (s1 > s0) s0 = s1;
       if (s0 < 0) s0 = 0;
       return path.substring(s0);
     }
   }
   return null;
 }
  public void setRequestMethod(String method) throws IOException {
    LOG.TRACE("setRequestMethod: " + method);
    /*
     * The request method can not be changed once the output stream has been
     * opened.
     */
    // if (streamConnection != null) {
    // throw new IOException("connection already open");
    // }

    if (!method.equals(HEAD) && !method.equals(GET) && !method.equals(POST)) {
      throw new IOException("unsupported method: " + method);
    }

    this.method = method;
  }
  void doDispatch(Properties reqHash, String strIndex) throws IOException {
    reqHash.setProperty("request-method", this.method);
    reqHash.setProperty("request-uri", uri.getPath());
    reqHash.setProperty("request-query", uri.getQueryString());

    if (postData != null && postData.size() > 0) {
      if (!RHOCONF().getBool("log_skip_post")) LOG.TRACE(postData.toString());
      reqHash.setProperty("request-body", postData.toString());
    }

    RubyValue res = RhoRuby.processRequest(reqHash, reqHeaders, resHeaders, strIndex);
    processResponse(res);

    RhodesApp.getInstance().keepLastVisitedUrl(url_external);
    LOG.INFO("dispatch end");
  }
  public void processRequest() throws IOException {
    if (!requestProcessed) {
      String strErr = "";

      LOG.TRACE("processRequest: " + getURL());
      String strReferer = reqHeaders != null ? reqHeaders.getPropertyIgnoreCase("Referer") : "";
      if (getRef() != null
          && getRef().length() > 0
          && strReferer != null
          && strReferer.equalsIgnoreCase(uri_orig.getPathNoFragment())) {
        respondNotModified();
      } else {
        String strContType = getContentType();

        if (uri.getPath().startsWith("/apps/public")) {
          httpServeFile(strContType);
        } else {
          if (this.method.equals("POST")
              || strContType.length() == 0
              || strContType.indexOf("application/x-www-form-urlencoded") >= 0) {
            if (dispatch()) {
              requestProcessed = true;
              return;
            }
          }

          if (
          /*this.method == "GET" &&*/ httpGetFile(strContType)) {

            // }else if ( dispatch() ){
          } else {
            respondNotFound(strErr);
          }
        }
      }
      requestProcessed = true;
    }
  }
  /**
   * Add the named field to the list of request fields. This method is where a subclass should
   * override properties.
   *
   * @param key key for the request header field.
   * @param value the value for the request header field.
   */
  protected void setRequestField(String key, String value) {
    LOG.TRACE("setRequestField: key = " + key + "; value = " + value);

    /*
     * If application setRequestProperties("Connection", "close") then we
     * need to know this & take appropriate default close action
     */
    // if ((key.equalsIgnoreCase("connection")) &&
    // (value.equalsIgnoreCase("close"))) {
    // ConnectionCloseFlag = true;
    // }

    /*
     * Ref . Section 3.6 of RFC2616 : All transfer-coding values are
     * case-insensitive.
     */
    // if ((key.equalsIgnoreCase("transfer-encoding")) &&
    // (value.equalsIgnoreCase("chunked"))) {
    // chunkedOut = true;
    // }

    reqHeaders.setPropertyIgnoreCase(key, value);
  }
 public String getResponseMessage() throws IOException {
   LOG.TRACE("getResponseMessage: " + responseMsg);
   processRequest();
   return responseMsg;
 }
 public String getHeaderFieldKey(int index) throws IOException {
   LOG.TRACE("getHeaderFieldKey: " + index);
   processRequest();
   if (index >= resHeaders.size()) return null;
   return ((String) (resHeaders.getKeyAt(index)));
 }
 public String getHost() {
   LOG.TRACE("getHost: " + uri.getHost());
   return uri.getHost();
 }
 public OutputStream openOutputStream() throws IOException {
   LOG.TRACE("openOutputStream");
   return postData;
 }
 public DataOutputStream openDataOutputStream() throws IOException {
   LOG.TRACE("openDataOutputStream");
   return new DataOutputStream(postData);
 }
 public InputStream openInputStream() throws IOException {
   LOG.TRACE("openInputStream");
   processRequest();
   return responseData;
 }
 public DataInputStream openDataInputStream() throws IOException {
   LOG.TRACE("openDataInputStream");
   return new DataInputStream(openInputStream());
 }
 public long getLastModified() throws IOException {
   LOG.TRACE("getLastModified");
   return getHeaderFieldDate("last-modified", 0);
 }
 public int getPort() {
   LOG.TRACE("getPort: " + uri.getPort());
   return uri.getPort();
 }
 public String getProtocol() {
   LOG.TRACE("getProtocol: " + uri.getScheme());
   return uri.getScheme();
 }
 public String getQuery() {
   LOG.TRACE("getQuery: " + uri.getQueryString());
   return uri.getQueryString();
 }
 public String getRef() {
   LOG.TRACE("getRef: " + uri.getFragment());
   return uri.getFragment() != null ? uri.getFragment() : "";
 }
 public String getRequestMethod() {
   LOG.TRACE("getRequestMethod: " + method);
   return method;
 }
  public int getResponseCode() throws IOException {
    processRequest();
    LOG.TRACE("getResponseCode" + responseCode);

    return responseCode;
  }
 public String getRequestProperty(String key) {
   LOG.TRACE("getRequestProperty: " + key);
   return reqHeaders.getPropertyIgnoreCase(key);
 }
 public void close() throws IOException {
   clean();
   LOG.TRACE("Close browser connection.");
 }
 public String getURL() {
   LOG.TRACE("getURL: " + url_external);
   return url_external;
 }