0

Using Flask and BlueMix to deploy a web app. Having some js issues that I cannot seem to figure out. I keep getting the same error in the browser console. I don't know any js so any help would be very appreciated!

jquery-1.11.1.min.js:4 POST http://newfla.mybluemix.net/ 405 (Method Not  Allowed)
send @ jquery-1.11.1.min.js:4
m.extend.ajax @ jquery-1.11.1.min.js:4 
(anonymous function) @ demo.js:66
m.event.dispatch @ jquery-1.11.1.min.js:3
r.handle @ jquery-1.11.1.min.js:3

Here is the supposed (anonymous function)

 $.ajax({
  type: 'POST',
  data: {
    text: $content.val()
  },
  url: '/',
  dataType: 'json',
  success: function(response) {
    $loading.hide();

    if (response.error) {
      showError(response.error);
    } else {
      $results.show();
      showTraits(response);
      showTextSummary(response);
      showVizualization(response);
    }

  }

UPDATE: I've tried a few different things matching your suggestions. Here is where I am now, any ideas?

consumer_token = 'aaaaaaaaaaaaaaaaaaaaaaaaa' #substitute values from twitter     website 
consumer_secret = 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'
access_token = '3473558363-aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'
access_secret = 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'

auth = tweepy.OAuthHandler(consumer_token,consumer_secret)
auth.set_access_token(access_token,access_secret)

api  = tweepy.API(auth)

class PersonalityInsightsService:
"""Wrapper on the Personality Insights service"""

def __init__(self, vcapServices):
"""
Construct an instance. Fetches service parameters from VCAP_SERVICES
runtime variable for Bluemix, or it defaults to local URLs.
"""


self.url = "https://gateway.watsonplatform.net/personality-insights/api"
self.username = "aaaaaa-vvvv-1111-2222-mmmmmmmm"
self.password = "password"

if vcapServices is not None:
    print("Parsing VCAP_SERVICES")
    services = json.loads(vcapServices)
    svcName = "personality_insights"
    if svcName in services:
        print("Personality Insights service found!")
        svc = services[svcName][0]["credentials"]
        self.url = svc["url"]
        self.username = svc["username"]
        self.password = svc["password"]
    else:
        print("ERROR: The Personality Insights service was not found")
def getProfile(self, text):
    """Returns the profile by doing a POST to /v2/profile with text"""

    if self.url is None:
        raise Exception("No Personality Insights service is bound to this app")
    response = requests.post(self.url + "/v2/profile",
                      auth=(self.username, self.password),
                      headers = {"content-type": "text/plain"},
                      data=text
                      )
    try:
        return json.loads(response.text)
    except:
        raise Exception("Error processing the request, HTTP: %d" % response.status_code)

class DemoService(object):
    """
    REST service/app. Since we just have 1 GET and 1 POST URLs,
    there is not even need to look at paths in the request.
    This class implements the handler API for cherrypy library.
    """

    screen_name = "realDonaldTrump"
    maxnumtweets= 500

    saveFile = open("static/public/text/en.txt",'a')
    saveFile.seek(0)
    saveFile.truncate()


    for status in     tweepy.Cursor(api.user_timeline,id=screen_name).items(maxnumtweets): 
    print status.text[0:2] + '\n'
    saveFile = open("static/public/text/en.txt",'a')

    textyt = status.text

    texty = ''.join(i for i in textyt if ord(i)<128)
    saveFile.write(texty.encode('utf-8')+'\n'+'\n')
    saveFile.close()

def __init__(self, service):
    self.service = service
    self.defaultContent = None

    try:
        contentFile = open("static/public/text/en.txt", "r")
        self.defaultContent = contentFile.read()
    except Exception as e:
        print "ERROR: couldn't read text file: %s" % e
    finally:
        contentFile.close()

def GET(self):
   return render_template('newin.html', content= self.defaultContent)




def POST(self, text=None):
    """
    Send 'text' to the Personality Insights API
    and return the response.
    """
    try:
        profileJson = self.service.getProfile(text)
        return json.dumps(profileJson)
    except Exception as e:
        print "ERROR: %s" % e
        return str(e)


@app.route('/')
def main():
    return render_template('index.html')

@app.route('/getpost', methods=['GET', 'POST'])
def new():
    personalityInsights = PersonalityInsightsService(os.getenv("VCAP_SERVICES"))
c = DemoService(personalityInsights)
if request.method == 'GET':
    return c.GET()
elif request.method == 'POST':
    return c.POST()
Matt
  • 74,352
  • 26
  • 153
  • 180
Beezley
  • 29
  • 1
  • 6
  • seems like you are trying to use Personality Insights. Take a look at the python-sdk: https://github.com/watson-developer-cloud/python-sdk/blob/master/examples/personality_insights_v2.py – German Attanasio Nov 07 '15 at 22:20
  • Thanks, German! I think the issue here is how unfamiliar I am with cherrypy. I was trying to convert this into a Flask based app, my issue being that I can't figure out how to initiate the POST. – Beezley Nov 07 '15 at 23:36
  • take a look at this flash app that uses the text to speech service https://github.com/watson-developer-cloud/text-to-speech-python – German Attanasio Nov 08 '15 at 05:12

1 Answers1

4

This isn't a Javascript issue. The view function that is serving the root URL is not configured to accept POST requests. Response code 405 is METHOD NOT ALLOWED (the method here being POST as opposed to GET, PUT, DELETE, OPTIONS, HEAD, etc...

I'm able to recreate it with a very simple hello world Flask app

app.py:

from flask import Flask

app = Flask(__name__)

@app.route('/')
def hello_world():
    return 'Hello World'

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

Running the app from the command line (will be made available at http://localhost:5000/):

python app.py

and then trying to post against it from another terminal (using the requests library):

import requests

response = requests.post('http://localhost:5000/', data='')

print response will yield:

<Response [405]>

Note the 405 - the same response code you received, method not allowed. You need to explicitly define any methods other than GET that you want your Flask views to use by updating the app.route decorator:

@app.route('/', methods=['GET', 'POST'])
def hello_world():
    return 'Hello World'

Generally however, you'll want to implement different functionality if a client does a POST instead of a GET. You can do this by looking at the request.method (you'll also need to import request):

from flask import Flask, request

app = Flask(__name__)

@app.route('/', methods=['GET', 'POST'])
def hello_world():
    if request.method == 'GET':
        return 'You GOT hello world'
    elif request.method == 'POST':
        return 'You POSTed hello world'

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

If you'd like to read more about the different HTTP methods, they are defined here.

chucksmash
  • 5,777
  • 1
  • 32
  • 41