Git Product home page Git Product logo

Comments (6)

corydolphin avatar corydolphin commented on July 17, 2024

@richardraseley this should be fixed in 1.1.1. Is there any chance you can update and let me know if the issue still exists?

Please excuse the strange versioning, I adopted semver after the 1.1 release (which should have been version 1.1.0)

Thanks for taking the time to report the issue, I really appreciate the feedback :-)

EDIT: I just saw your #11, any chance you can help to shed light on what the issue was? Even though you figured it out, feedback on the documentation would be awesome too!

from flask-cors.

richardraseley avatar richardraseley commented on July 17, 2024

@wcdolphin Thank you for your reply.

Running pip list reports I am running Flask-Cors (1.1.1). Should I remove via pip and install manually?

from flask-cors.

corydolphin avatar corydolphin commented on July 17, 2024

Hmm, that is strange. I tried to reproduce the bug on my machine, but couldn't.

Two quick notes/asks:

  1. I see you are using Python 2.6.6, which shouldn't be an issue (testing against Python 2.6 is automated)
  2. I will explicitly ask travis to test against 2.6.6 and see if I can reproduce the issue!
  3. Can you share your code so I can better replicate your setup?
  4. Here is the steps I used to attempt to reproduce the issue:

I created a new virtualenv, installed 1.1.1 and modified the example.py to include Content-Type:

from flask import Flask, request
from flask.ext.cors import cross_origin

app = Flask(__name__)


@app.route("/")
@cross_origin(headers='Content-Type')
def helloWorld():
    return '''<h1>Hello CORS!</h1> Read about my spec at the
<a href="http://www.w3.org/TR/cors/">W3</a> Or, checkout my documentation
on <a href="https://github.com/wcdolphin/flask-cors">Github</a>'''

if __name__ == "__main__":
    app.run(debug=True)

Using curl, I saw the expected header:

➜  curl -I http://localhost:5000
HTTP/1.0 200 OK
Content-Type: text/html; charset=utf-8
Content-Length: 184
Access-Control-Allow-Origin: *
Access-Control-Allow-Methods: GET, HEAD, OPTIONS, POST, PUT
Access-Control-Allow-Headers: Content-Type
Server: Werkzeug/0.9.4 Python/2.7.5
Date: Fri, 14 Feb 2014 23:56:30 GMT

Thanks again for helping!

from flask-cors.

richardraseley avatar richardraseley commented on July 17, 2024

@wcdolphin Implementing your specific example on my box, the header came back as expected. Upon further jiggling my script around I found that I had to also add the header to the route that accepted the GET verb, even though I had already added it to the route that accepted both the POST and OPTIONS verbs.

This is an odd behavior for me, as when doing an $ajax.getjson request my understanding is that there would be a preflight OPTIONS request to the URL before the POST - but not a GET.

Sorry for the false alarm, but I really appreciate your prompt replies and willingness to help.

Thanks so much for your work on this useful tool!

from flask-cors.

corydolphin avatar corydolphin commented on July 17, 2024

Interesting, can you share your original code?

I fear the initial example may be confusing, as I unnecessarily declare both GET and OPTIONS methods. In reality, no end-user should have to think about the OPTIONS preflight, as the flask-cors defaults to overriding Flask's builtin default OPTIONS response handler, which simply returns an empty response with Allow headers.

Thanks for working through it with me, happy to help however I can!

Cheers!

from flask-cors.

richardraseley avatar richardraseley commented on July 17, 2024

The faulty code wasn't preserved in a commit that I can find. That being said, here is the currently working code:

#!/usr/bin/python

from flask import abort,Flask,jsonify,make_response,request
from flask.ext.cors import cross_origin
import redis
import uuid

app=Flask(__name__)
r=redis.StrictRedis(host='localhost',port='6379',db=0)

@app.route('/api/v1.0/assets',methods=['GET'])
@cross_origin(headers='Content-Type')
def get_assets():
  exists=r.exists('assets')
  if not exists:
    abort(404)
  else:
    members=r.smembers('assets')
    assets=[]
    for member in members:
      assets.append(member)
    return jsonify({'result':'success','data':assets})

@app.route('/api/v1.0/assets',methods=['POST','OPTIONS'])
@cross_origin(headers='Content-Type')
def post_assets():
  json=request.get_json()
  if not 'type' in json:
    abort(400)
  else:
    id=uuid.uuid4()
    r.sadd('assets',id)
    r.sadd('types',json['type'])
    r.sadd('types_'+json['type'],id)
    r.hset(id,'type',json['type'])
    for key,value in json.iteritems():
      if key != 'type':
        r.hset(id,key,value)
    return jsonify({'result':'success','data':id})

@app.route('/api/v1.0/assets',methods=['OPTIONS'])
@cross_origin()
def options_assets():
  return 200

@app.route('/api/v1.0/assets/<asset>',methods=['GET'])
@cross_origin()
def get_assets_asset(asset):
  exists=r.exists(asset)
  if not exists:
    abort(404)
  else:
    properties=r.hgetall(asset)
    hash={}
    hash[asset] = properties
    return jsonify({'result':'success','data':hash})

@app.route('/api/v1.0/assets/<asset>',methods=['DELETE'])
@cross_origin()
def delete_assets_asset(asset):
  exists=r.exists(asset)
  if not exists:
    abort(404)
  else:
    properties=r.hgetall(asset)
    r.srem('assets',asset)
    r.srem('types_'+properties['type'],asset)
    members = r.smembers('types_'+properties['type'])
    if not members:
      r.srem('types',properties['type'])
    r.delete(asset)
    return jsonify({'result':'success','data':'deleted'})

@app.route('/api/v1.0/types',methods=['GET'])
@cross_origin()
def get_types():
  exists=r.exists('types')
  if not exists:
    abort(404)
  else:
    members=r.smembers('types')
    types=[]
    for member in members:
      types.append(member)
    return jsonify({'result':'success','data':types})

@app.route('/api/v1.0/types/<type>', methods = ['GET'])
@cross_origin()
def get_types_type(type):
  exists=r.exists('types_'+type)
  if not exists:
    abort(404)
  else:
    members=r.smembers('types_'+type )
    assets=[]
    for member in members:
      assets.append(member)
    return jsonify({'result':'success','data':assets})

@app.errorhandler(400)
def not_found(error):
  return make_response(jsonify({'result':'error','data':'bad request'}),400)

@app.errorhandler(404)
def not_found(error):
  return make_response(jsonify({'result':'error','data':'url not found'}),404)

@app.errorhandler(500)
def not_found(error):
  return make_response(jsonify({'result':'error','data':'internal server error'}),500)

if __name__ == '__main__':
  app.run(host='0.0.0.0', debug=True)

This will just require a bone stock redis instance (>= 2.8.x) on the localhost. My thought is you can reproduce it with removing headers='Content-Type' from the first GET route.

Sorry I can't be more specific - there were lots of pre-commit changes in a short period of time.

from flask-cors.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.