How to execute query in Odoo-8 from Python? - python

I have the following function in the class hr_evaluation_interview:
#api.onchange('evaluation_id')
def onchange_evalID(self):
self.deadline=self.env.cr.execute('SELECT date FROM hr_evaluation_evaluation where id=119')
Note: I'm just giving id=119 in the query for testing purposes.
When I give self.deadline=datetime.now.strftime(%Y-%m-%d %H:%M:%S") it works fine and changes the value of field deadline when the value of field evaluation_id changes. Again for just testing.
What I really need is to execute a query similar to what I mentioned. However when I execute this query nothing is printing on the deadline field. When I check the log I see this warning:
WARNING db_name openerp.models: Cannot execute name_search, no _rec_name defined on hr_evaluation.evaluation
I tried checking online why this warning, but got no help. Am I doing something wrong? How exactly can I execute query from within #api.onchange(self)?

As Hardik said, cr.execute() doesn't return directly you result. You need to fetch the values from the cursor after executing the query. Try like this:
#api.onchange('evaluation_id')
def onchange_evalID(self):
self.env.cr.execute('SELECT date '
'FROM hr_evaluation_evaluation where id=119')
self.deadline = self.env.cr.fetchone()[0]

If evaluation_id is m2o field of hr.evaluation.evaluation model you can try below code. you don't need to execute query at all.
#api.onchange('evaluation_id')
def onchange_evalID(self):
if self.evaluation_id and self.evaluation_id.date:
self.date = self.evaluation_id.date

Related

SQLAlchemy/Postgres: Intermittent Error Serializing Object After Commit

I have a Flask application that uses SQLAlchemy (with some Marshmallow for serialization and deserialization).
I'm currently encountering some intermittent issues when trying to dump an object post-commit.
To give an example, let's say I have implemented a (multi-tenant) system for tracking system faults of some sort. This information is contained in a fault table:
class Fault(Base):
__tablename__ = "fault"
fault_id = Column(BIGINT, primary_key=True)
workspace_id = Column(Integer, ForeignKey('workspace.workspace_id'))
local_fault_id = Column(Integer)
name = Column(String)
description = Column(String)
I've removed a number of columns in the interest of simplicity, but this is the core of the model. The columns should be largely self explanatory, with workspace_id effectively representing tenant, and local_fault_id representing a tenant-specific fault sequence number, which is handled via a separate fault_sequence table.
This fault_sequence table holds a counter against workspace, and is updated by means of a simple on_fault_created() function that is executed by a trigger:
CREATE TRIGGER fault_created
AFTER INSERT
ON "fault"
FOR EACH ROW
EXECUTE PROCEDURE on_fault_created();
So - the problem:
I have a Flask endpoint for fault creation, where we create an instance of a Fault entity, add this via a scoped session (session.add(fault)), then call session.commit().
It seems that this is always successful in creating the desired entities in the database, executing the sequence update trigger etc. However, when I then try to interrogate the fault object for updated fields (after commit()), around 10% of the time I find that each key/field just points to an Exception:
psycopg2.errors.InFailedSqlTransaction: current transaction is aborted, commands ignored until end of transaction block
Which seems to boil down to the following:
(psycopg2.errors.InvalidTextRepresentation) invalid input syntax for integer: ""
[SQL: SELECT fault.fault_id AS fault_fault_id, fault.workspace_id AS fault_workspace_id, fault.local_fault_id AS fault_local_fault_id, fault.name as fault_name, fault.description as fault_description
FROM fault
WHERE fault.fault_id = %(param_1)s]
[parameters: {'param_1': 166}]
(Background on this error at: http://sqlalche.me/e/13/2j8
My question, then, is what do we think could be causing this?
I think it smells like a race condition, with the update trigger not being complete before SQLAlchemy has tried to get the updated data; perhaps local_fault_id is null, and this is resulting in the invalid input syntax error.
That said, I have very low confidence on this. Any guidance here would be amazing, as I could really do with retrieving that sequence number that's incremented/handled by the update trigger.
Thanks
Edit 1:
Some more info:
I have tried removing the update trigger, in the hope of eliminating that as a suspect. This behaviour is still intermittently evident, so I don't think it's related to that.
I have tried adopting usage of flush and refresh before the commit, and this allows me to get the values that I need - though commit still appears to 'break' the fault object.
Edit 2:
So it really seems to be more postgres than anything else. When I interrogate my database logs, this is the weirdest thing. I can copy and paste the command it says is failing, and I struggle to see how this integer value in the WHERE clause is possibly evaluating to an empty string.
This same error is reproducible with SELECT ... FROM fault WHERE fault.fault_id = '', which in no way seems to be the query making to the DB.
I am stumped.
Your sentence "This same error is reproducible with SELECT ... FROM fault WHERE fault.fault_id = '', which in no way seems to be the query making to the DB." seems to indicate that you are trying to access an object that does not have the database primary key "fault_id".
I guess, given that you did not provide the code, that you are adding the object to your session (session.add), committing (session.commit) and then using the object. As fault_id is autogenerated by the database, the fault object in the session (in memory) does not have fault_id.
I believe you can correct this with:
session.add(fault)
session.commit()
session.refresh(fault)
The refresh needs to be AFTER commit to refresh the fault object and retrieve fault_id.
If you are using async, you need
session.add(fault)
await session.commit()
await session.refresh(fault)

Error while executing the query in SqlLite3

I am trying to add username, user id and many other variables after the user press /start in Telegram bot. But I am getting an error in this code
def add_user(userid, username):
userCount = c.execute(f"COUNT({userIdColumn} FROM {info_table} WHERE {userIdColumn}={userid}")
if(userCount <= 0):
c.execute(f"INSERT INTO {info_table}({userIdColumn},{usernameColumn},{isBannedColumn},{isSubscribedColumn},{userNotesColumn}) VALUES ({userid},{username},0,1,' ')")
c.commit()
db.close()
I tried declaring cursor() and even database inside the function but the errors I get are
sqlite3.ProgrammingError: SQLite objects created in a thread can only be used in that same thread. The object was created in thread id 20532 and this is thread id 19184.
sqlite3.OperationalError: near "COUNT": syntax error
I am also aware that there is a post about the same problem which unfortunately did not solved my problem.
My question is what is the correct declaration here?
The fix for the first error was adding check_same_thread=False as a paramter = sqlite3.connect("Your db",check_same_thread=False) and also you need to declare the cursor() inside the function
The second error was caused by wrong format as it should be SELECT COUNT

How to use Azure DevOps / VSTS to fetch query results in python

Below is my current code. It connects successfully to the organization. How can I fetch the results of a query in Azure like they have here? I know this was solved but there isn't an explanation and there's quite a big gap on what they're doing.
from azure.devops.connection import Connection
from msrest.authentication import BasicAuthentication
from azure.devops.v5_1.work_item_tracking.models import Wiql
personal_access_token = 'xxx'
organization_url = 'zzz'
# Create a connection to the org
credentials = BasicAuthentication('', personal_access_token)
connection = Connection(base_url=organization_url, creds=credentials)
wit_client = connection.clients.get_work_item_tracking_client()
results = wit_client.query_by_id("my query ID here")
P.S. Please don't link me to the github or documentation. I've looked at both extensively for days and it hasn't helped.
Edit: I've added the results line that successfully gets the query. However, it returns a WorkItemQueryResult class which is not exactly what is needed. I need a way to view the column and results of the query for that column.
So I've figured this out in probably the most inefficient way possible, but hope it helps someone else and they find a way to improve it.
The issue with the WorkItemQueryResult class stored in variable "result" is that it doesn't allow the contents of the work item to be shown.
So the goal is to be able to use the get_work_item method that requires the id field, which you can get (in a rather roundabout way) through item.target.id from results' work_item_relations. The code below is added on.
for item in results.work_item_relations:
id = item.target.id
work_item = wit_client.get_work_item(id)
fields = work_item.fields
This gets the id from every work item in your result class and then grants access to the fields of that work item, which you can access by fields.get("System.Title"), etc.

calling msdb.sp_send_dbmail via pyodbc

I am attempting to call a sproc that wraps T-SQL's sp_send_dbmail procedure. It simply creates the query, and then passes that and a hardcoded subject and recipient to the Microsoft supplied sproc. When running from sql management studio, the sproc executes as expected and I receive an email. From pyodbc, it doesn't send an email. The contents of my sproc look similar to:
declare #qry varchar(MAX)
set #qry = 'select * from table'
EXEC msdb.dbo.sp_send_dbmail
#recipients = 'email#email.com',
#subject = 'my email',
#query = #qry
select * from table
where 1=0
I have also tried toggling the #exclude_query_output, flag but that had no effect. I am invoking that sproc via the following method:
def execute_sproc(query, cnxn):
cursor = cnxn.cursor();
rows = cursor.execute(query)
columns = [column[0] for column in cursor.description]
return pd.DataFrame.from_records(rows, columns=columns)
where the query is simply executing my wrapper sproc. As I mentioned before, the wrapper sproc works when run from the management studio, but no email is sent when called here. I am using the same credentials to access my database in both places. I have also used this function to successfully call other sprocs, but none of them have contained exec statements, nor have they done many of the other things that im sure sp_send_dbmail is doing.
Please let me know if you have any ideas.
Thanks,
Max Goldman
So i think this comes down to a misunderstanding of either the sendmail sproc, pyodbc, or both. I have another method for calling sprocs that edit the database:
def execute_commit_sproc(query, cnxn):
cursor = cnxn.cursor();
cursor.execute(query)
cnxn.commit()
The only difference being that the former expected a result set, whereas the latter makes changes to the db, and uses pyodbc's commit mechanism to save the results. I did not realize the sp_send_dbmail required this to be called in order for the email to be sent. I am still unsure of why (what is getting written to, what pyodbc::commit() is doing under the hood, etc.)

Keeps getting "error binding parameter 0 - probably unsupported type"

I'm using eric4 (qtdesigner, pyqt, python, etc) with sqlite and I keep getting "error binding parameter 0 - probably unsupported type" when I'm running the program I've coded.
I've made some GUIs using eric4 + qtdesigner and generated dialog codes. When one of the buttons of the windows I've made in qtdesigner are pressed, it should access the database and would then commits and saves the information in the database. I've made a separate py file for accessing and saving for the database.
Here are parts of my code which are most likely sources of the error I keep getting.
At generated dialog of the ui (which I imported the separate py file):
def on_button_Save_released(self):
"""
Slot documentation goes here.
"""
# TODO: not implemented yet
Nik = self.LineEdit_Nickname.text()
NFirst = self.LineEdit_NameFirst.text()
NMid = self.LineEdit_NameMiddle.text()
NLast = self.LineEdit_NameLast.text()
BMon = self.ComboBox_BirthMonth.currentText()
BDay = self.ComboBox_BirthDay.currentText()
BYear = self.ComboBox_BirthYear.currentText()
CNum = self.LineEdit_ContactNum.text()
EM = self.LineEdit_EMail.text()
MAd = self.LineEdit_MailAdd.text()
self.NMem = NewMem()
self.NMem.input_data(Nik, NFirst, NMid, NLast, BMon, BDay, BYear, CNum, EM, MAd)
And this at the database accessing and writing which is on a separate py file:
import sqlite3
import datetime, time
con = sqlite3.connect("Members.db") #access database
cur = con.cursor() #cursor object for database
class NewMem:
def input_data(self, Nik, NFirst, NMid, NLast, BMon, BDay, BYear, CNum, EM, MAd):
def adapt_datetime(ts):
return time.mktime(ts.timetuple())
#Get current time and date
sqlite3.register_adapter(datetime.datetime, adapt_datetime)
now = datetime.datetime.now()
#created if first time to make a table
try:
cur.execute('create table Members (ID integer primary key autoincrement not null, Nick string not null, NameFirst string, NameMiddle string, NameLast string, BirthMonth string, BirthDay string, BirthYear string, ContactNum string, EMail string, MailAdd string, MemberSince string)')
except:
pass
cur.execute("insert into Members (Nick,NameFirst,NameMiddle,NameLast,BirthMonth,BirthDay,BirthYear,ContactNum,EMail,MailAdd,MemberSince) values (?,?,?,?,?,?,?,?,?,?,?)",(Nik, NFirst, NMid, NLast, BMon, BDay, BYear, CNum, EM, MAd, now))
con.commit()
cur.close()
con.close()
I've read some searches at google that it might be the quotation marks and ? parameters but I've checked and they are correct it seems. Also read somewhere that it has to do with the character map (UTF?) but I honestly don't know how to check...
I've also added some print to see if they are showing the correct data I've input and they are correct. So it's quite boggling why I'm still getting the error.
Any help is much appreciated bows deeply
QlineEdit.text() returns a QString. Pass it to the unicode constructor to get something usable.
I was sort of able to reproduce this.
If you pass a string or a number or even a date as Nik, everything works. The error you describe happens only if you pass something strange as Nik, e.g. a class or a function.
Check that invocations of input_data pass a correct Nik. Most probably a () is forgotten somewhere so a class or a function is passed instead of an instance or function's result.

Categories

Resources