Plugins:GenericHttpMethod

From MozillaWiki
Jump to: navigation, search

Status

Under Consideration

Problem Summary

  1. The plugin API only supports GET and POST. It would be desirable to support other methods defined in RFC 2616, such as DELETE, OPTIONS, and PUT, and also extension methods such as PROPFIND (WebDAV) or PATCH.
  2. HTTP request headers can only be set for POST (see NPN_PostURLNotify), but not for GET (NPN_GetURLNotify). This makes it hard to access content-negotiated resources and to control caching (such as by taking advantage of conditional requests).
  3. There is insufficient control over handling HTTP redirects. If a redirect is followed automatically, the caller should be able to find out the type of redirect (temporary or permanent) and the new URI. If a redirect was not followed, it should have access to status code and Location header. And finally it should be able to select whether redirects are followed or not. (Note that currently this isn't covered by XmlHttpRequest either, but is a known to-do)
  4. Confusion about how invalid URLs (for instance, containing non-ASCII characters or whitespace) need to be handled.

Future extensions we should plan for:

  1. Access to provisional 1xx responses.
  2. Access to HTTP trailer information.
  3. Interaction with security-related extensions, such as CORS or Strict Transport Security.

Existing Discussions and Documentation

Related Documentation

  • XMLHttpRequest (demonstrates that browsers already support the required functionality and could be used to define certain behaviors, such as how request headers are defaulted and combined)
  • Mark Nottingham's XmlHttpRequest Test Cases

API Requirements

Current Proposal

  • Last modified: September 30, 2009
  • Author: Darin Fisher (Google) and Julian Reschke (greenbytes)
  • Contributors: Ian Melven (Adobe)

The current proposal is to add a new method inspired by NPP_URLNotify, adding the missing pieces:

NPError NPN_HttpRequest(
  NPP instance,
  PRUint64 flags, // control redirects etc
  const char* method,
  const char* url,
  const char* target,
  const char* headers,
  PRUint64 len,
  const char* buf,
  NPBool file,
  void* notifyData);

and have a matching plugin method that would be called everytime the request state changes (see XHR readyState).

void NPP_HttpResponseNotify(
  NPP instance,
  const char* url,
  int readyState, // http://www.w3.org/TR/XMLHttpRequest/#states
  int httpResponseStatus,
  const char* headers, // potentially including the status line
  void* notifyData);

A callback with readyState == DONE would then signal the completion of the request.

To address potential security issues with certain HTTP methods (for instance, TRACE), and to allow easier deployment, support for methods other than GET and POST would only be RECOMMENDED, and a new status code (see below) allows the caller to detect this condition.

New NPError codes:

// HTTP stack does not support method
#define NPERR_METHOD_NOT_SUPPORTED (NPERR_BASE + nn)

Redirect Handling

We currently consider two use cases with respect to handling HTTP redirects:

  1. "best effort" - follow redirects automatically, when allowed
  2. "full control for plugin" - expose all information to the caller, and let it decide

In the second mode, the method would treat an HTTP redirect just like any other HTTP status. This means that the caller needs to detect the status (3xx), and obtain the Location response header to follow the redirect.

Open Issues

  • Do we need a separate callback for the final state (as in NPN_PostURLNotify, or should we just keep calling NPP_HttpResponseNotify and add a status field as in XmlHttpRequest?) This may be obvious from the calling sequence, but we certainly need to clarify and add examples
  • Is there a better way to pass in flags than setting bits in an integer parameter? Seems to be an acceptable approach; need to be clear about what the defaults are though
  • Error handling in XHR (due to historical reasons) is a weird mix involving readyState, httpResponseState (going back to 0) and exceptions; we should do better than that.
  • Do we need a way to abort a request? Yes. Return code from the notify callback, or new function?
  • Should we provide a utility method for extracting header values from the headers char*? We have discussed this on the mailing list, and there is strong consensus to keep access to the raw header information, but also support for providing a convenience method for parsing, potentially as open-sourced reference implementation though
  • Should same-origin policy apply? If not, should the plugin be able to opt in?
  • Make it easier for plugins to follow a redirect? (creating a new request may be more work than it should be)
  • need to clarify encoding in filename and URL parameters (for old methods as well)
  • do we need to be able to specify a timeout?
  • would it be better to put all the parameters in a versioned struct?