Problem querying from a model object - python

I'm trying to use Pylons with SqlAlchemy (through Elixir).
Here is my testdb/model/entities.py:
from elixir import *
metadata.bind = "mysql://testdb:hundertwasser#localhost/testdb"
metadata.bind.echo = True
class Post(Entity):
text = Field(Unicode(128))
And here is the controller:
import logging
from pylons import request, response, session, tmpl_context as c, url
from pylons.controllers.util import abort, redirect
from testdb.lib.base import BaseController, render
log = logging.getLogger(__name__)
from testdb.model.entities import *
class MainController(BaseController):
def index(self):
c.posts = Post.query.all()
print "Test"
return render('/index.mako')
def submit(self):
post = Post()
post.text = request.POST.get['text']
session.commit()
When I run the application, I get an error saying:
AttributeError: type object 'Post' has no attribute 'query'
Does someone know what I'm doing wrong?

The answer is as follows:
entities.py is missing the following two lines at the bottom:
setup_all()
create_all()

I don't know Elixir well, but isn't putting the following in the .ini enough?
sqlalchemy.url = mysql://user:pass#localhost/dbname?charset=utf8&use_unicode=0
sqlalchemy.pool_recycle = 3600
All the stuff after ? is to avoid encoding problems. The second line prevents MySQL from closing inactive connections (in fact it reconnects every hour).

Related

Syntax error When I try to run backend code

When I try to run the server I get syntax error. But there isn`t any incorrect using of syntax. Please help to correct this issue! Issue image
from blacksheep.server.application import Application
from blacksheep.server.controllers import Controller, get, post
from blacksheep.cookies import Cookie
from blacksheep.messages import Response
from easy_cryptography.hash.hash_funct import compare_hash
from app.configuration import AUTHORIZED
from models import Doctors
from pony.orm import *
class Home(Controller):
#get("/")
def index(self):
return self.view()
class Patients(Controller):
#post("/patients")
def patients(self, login: str, password: str):
if Doctors.exists(login) and (compare_hash(password, Doctors.get_for_update(login = login).password)):
patients = Patients.select()
response = self.view(patients=patients)
response.set_cookie(Cookie(AUTHORIZED,True))
return response
else:
return "{'message':'Неверный логин или пароль'}"
It looks like you are missing the async keyword before def index(self):
Another bug I can see is that you are not binding the parameters to your patients method correctly from the #post decorator.

connecting mongodb server via seperate class

I am using flask to create simple api. The api simply returns values from mongoDB. Everything works great if i do the connection within same function. I am not doing connection simply at start of file because i am using uwsgi and nginx server on ubuntu. If i do that then there will be a problem of fork.
However, I have to use this connection with other api so thought to make a seperate class for connection and each api will simply call it . I m using this functionality to make codes manageable. However when i try the these codes it always shows internal server error. I tried making this function static too , still the error exists.
Note - I have replaced mongodb address with xxx as i am using mongodbatlas account here
from flask import Flask
from flask import request, jsonify
from flask_pymongo import pymongo
from pymongo import MongoClient
from flask_restful import Resource, Api, reqparse
app = Flask(__name__)
api = Api(app)
#client = MongoClient("xxx")
#db = client.get_database('restdb')
#records = db.stars
class dbConnect():
def connect(self):
client = MongoClient("xxx")
db = client.get_database('restdb')
records = db.stars
return records
class Order(Resource):
def get(self):
#client = MongoClient("xxx")
#db = client.get_database('restdb')
#records = db.stars
#star = records
star = dbConnect.connect
output = []
for s in star.find():
output.append({'name' : s['name'], 'distance' : s['distance']})
return jsonify({'result' : output})
api.add_resource(Order, '/')
if __name__ == "__main__":
app.run(host='0.0.0.0')
ERROR {"message": "Internal Server Error"}
Preliminary investigation suggests that you haven't instantiated your dbConnect class. Also, you haven't called the method connect properly.
class Order(Resource):
def get(self):
db = dbConnect() # This was missing
star = db.connect() # This is how you make method call properly.
output = []
for s in star.find():
output.append({'name' : s['name'], 'distance' : s['distance']})
return jsonify({'result' : output})
Also class dbConnect() should be declared as class dbConnect:.

How to set the return value of a get request in an unit test?

I am trying to set the return value of a get request in python in order to do a unit test, which tests if the post request is called with the correct arguments. Assume I have the following code to test
# main.py
import requests
from django.contrib.auth.models import User
def function_with_get():
client = requests.session()
some_data = str(client.get('https://cool_site.com').content)
return some_data
def function_to_test(data):
for user in User.objects.all():
if user.username in data:
post_data = dict(data=user.username)
else:
post_data = dict(data='Not found')
client.post('https://not_cool_site.com', data=post_data)
#test.py
from unittest import mock
from unittest import TestCase
from main import function_with_get, function_to_test
class Testing(TestCase):
#mock.patch('main.requests.session')
def test_which_fails_because_of_get(self, mock_sess):
mock_sess.get[0].return_value.content = 'User1'
data = function_with_get()
function_to_test(data)
assertIn('Not Found', mock_sess.retrun_value.post.call_args_list[1])
This, sadly, does not work and I have also tried to set it without content, however, I get an error AttributeError: 'str' object has no attribute 'content'
What would be the correct way to set the return_value of the get request, so that I can test the arguments of the post request?
I think you almost have it, except you're missing the return value for session() - because session is instantiated to create the client instance. I think you can drop the [0] too.
Try:
mock_sess.return_value.get.return_value.content = 'User1'
Try with .text because this should work for strings.
s = requests.Session()
s.get('https://httpbin.org/cookies/ set/sessioncookie/123456789')
r = s.get('https://httpbin.org/ cookies')
print(r.text)
http://docs.python-requests.org/en/master/user/advanced/

Session data not being stored during testing in Django

I am currently writing tests for our project, and I ran into an issue. We have this section of a view, which will redirect the user back to the page where they came from including an error message (that's being stored in the session):
if request.GET.get('error_code'):
"""
Something went wrong or the call was cancelled
"""
errorCode = request.GET.get('error_code')
if errorCode == 4201:
request.session['errormessage'] = _('Action cancelled by the user')
return HttpResponseRedirect('/socialMedia/manageAccessToken')
Once the HttpResponseRedirect kicks in, the first thing that the new view does is scan the session, to see if any error messages are stored in the session. If there are, we place them in a dictionary and then delete it from the session:
def manageAccessToken(request):
"""
View that handles all things related to the access tokens for Facebook,
Twitter and Linkedin.
"""
contextDict = {}
try:
contextDict['errormessage'] = request.session['errormessage']
contextDict['successmessage'] = request.session['successmessage']
del request.session['errormessage']
del request.session['successmessage']
except KeyError:
pass
We should now have the error message in a dictionary, but after printing the dictionary the error message is not there. I also printed the session just before the HttpResponseRedirect, but the session is an empty dictionary there as well.
This is the test:
class oauthCallbacks(TestCase):
"""
Class to test the different oauth callbacks
"""
def setUp(self):
self.user = User.objects.create(
email='test#django.com'
)
self.c = Client()
def test_oauthCallbackFacebookErrorCode(self):
"""
Tests the Facebook oauth callback view
This call contains an error code, so we will be redirected to the
manage accesstoken page. We check if we get the error message
"""
self.c.force_login(self.user)
response = self.c.get('/socialMedia/oauthCallbackFacebook/',
data={'error_code': 4201},
follow=True,
)
self.assertEqual('Action cancelled by the user', response.context['errormessage'])
It looks like the session can not be accessed or written to directly from the views during testing. I can, however, access a value in the session by manually setting it in the test by using the following bit of code:
session = self.c.session
session['errormessage'] = 'This is an error message'
session.save()
This is however not what I want, because I need the session to be set by the view as there are many different error messages in the entire view. Does anyone know how to solve this? Thanks in advance!
After taking a closer look I found the issue, it is in the view itself:
errorCode = request.GET.get('error_code')
if errorCode == 4201:
request.session['errormessage'] = _('Action cancelled by the user')
The errorCode variable is a string, and I was comparing it to an integer. I fixed it by changing the second line to:
if int(errorCode) == 4201:

pool for Odoo objects from http.Controller class (python)

I'm new to Odoo (openERP) and python. I have an http.Controller in which I'm trying to retrieve a template which should contain some objects from openERP database, more specifically fleet_vehicle_log_fuel_obj.
Usually the self.pool.get() method should do the trick, but in controller it doesn't work.
I'm trying to send some objects to the client and process them with javascript.
Here's my controller:
import json
from openerp import SUPERUSER_ID, pooler
from openerp.addons.web import http
from openerp.addons.web.http import request
class google_map(http.Controller):
#http.route(['/google_map'], type='http', auth="public", website=True)
def google_map(self, *arg, **post):
cr, uid, context = request.cr, request.uid, request.context
fleet_vehicle_log_fuel_obj = self.pool.get('fleet_vehicle_log_fuel');
#fleet_vehicle_log_fuel_obj = pool.get('fleet_vehicle_log_fuel')
ids = fleet_vehicle_log_fuel_obj.search(cr, uid, [])
return request.website.render("fleet.google_map", json.dumps(ids))
the error I get is 'google_map' object has no attribute 'pool'. How can i get all the objects of a certain type and send them to the client?
I know I have arrived too late, but may be this helps to someone.
The http library allows you to access the models from the controller, so you should write:
import openerp.http as http
fleet_vehicle_log_fuel_obj = http.request.env['fleet_vehicle_log_fuel']
And then you will be able to apply any ORM method with fleet_vehicle_log_fuel_obj.
Try this:
pool = request.registry
model_obj = pool['your.model']
or
model_obj = request.registry['your.model']
Hope this will help you...
I haven't tested this but try add to import:
import openerp.pooler as pooler
Then use the code
osv_pool = pooler.get_pool(dbname)
osv_pool.get(model)
I got this from openerp/osv/osv.py

Categories

Resources