skip to navigation
skip to content

Not Logged In

wsgicors 0.6.0

WSGI for Cross Origin Resource Sharing (CORS)


This is a WSGI middleware that answers CORS preflight requests and adds the needed header to the response. For CORS see:


Either plug it in programmatically as in this pyramid example:

def app(global_config, **settings):
    """ This function returns a WSGI application.

    It is usually called by the PasteDeploy framework during
    ``paster serve``.

    def get_root(request):
        return {}

    config = Configurator(root_factory=get_root, settings=settings)
    # whatever it takes to config your app goes here

    from wsgicors import CORS
    return CORS(config.make_wsgi_app(), headers="*", methods="*", maxage="180", origin="*")

or plug it into your wsgi pipeline via paste ini to let it serve by waitress for instance:

 use = egg:mysuperapp#app

 # wsgi server configuration

 use = egg:waitress#main
 host =
 port = 6543

 pipeline =

 use = egg:wsgicors#middleware
 # define a "free" policy
 free_methods=HEAD, OPTIONS, GET

 # define a "subdom" policy
 subdom_origin= https://*
 subdom_expose_headers=Foo, Doom

 # define a combination of policies, they are evaluated in the order given by the policy keyword
 # the first that matches the request's origin will be used

Keywords are:

  • origin
  • headers
  • methods
  • credentials
  • maxage

for origin:

  • use copy which will copy whatever origin the request comes from
  • a space separated list of hostnames - they can also contain wildcards like * or ? (fnmatch lib is used for matching). If a match is found the original host is returned.
  • any other literal will be be copied verbatim (like * for instance to allow any source)

for headers:

  • use * which will allow whatever header is asked for
  • any other literal will be be copied verbatim

for expose_headers:

  • use * to allow access to any header the client might wish to access
  • any other literal will be be copied verbatim

for methods:

  • use * which will allow whatever method is asked for
  • any other literal will be be copied verbatim (like POST, PATCH, PUT, DELETE for instance)

for credentials:

  • use true
  • anything else will be ignored (that is no response header for Access-Control-Allow-Credentials is sent)

for maxage:

  • give the number of seconds the answer can be used by a client, anything nonempty will be copied verbatim

As can be seen in the example above, a policy needs to be created with the policy keyword. The options need then be prefixed with the policy name and a _. The policy keyword itself can be a comma separated list. If so the origin of the request is matched against the origins defined in the policies and the first matching is the policy used.


Version 0.6.0

  • support for multiple policies
  • caching of matching results

Version 0.5.1

  • check for request being preflight
  • reworked tests

Version 0.5.0

  • support for Access-Control-Expose-Headers
  • Header Vary is set to Origin if origin policy differs from *

Version 0.4.1

  • py3 utf-8 related setup fixes

Version 0.4

  • python3 compatibility

Version 0.3

  • origin now takes space separated list of hostnames. They can be filename patterns like *.domain.tld

Version 0.2

  • Access-Control-Allow-Credentials is now returned in the actual reponse if specified by policy


“wsgicors” is written and maintained by Norman Krämer.


The following people contributed directly or indirectly to this project:

Please add yourself here when you submit your first pull request.

File Type Py Version Uploaded on Size
wsgicors-0.6.0.tar.gz (md5) Source 2015-09-16 12KB
  • Downloads (All Versions):
  • 197 downloads in the last day
  • 943 downloads in the last week
  • 3560 downloads in the last month