SteveFossey | 2023-09-06 02:11:37 UTC | #1 Just a fun little piece I know I'll want to look up later, in case it's useful. I'm supporting ETQ in getting data from our system. They use Python scripts so I'm using that to prove anything I claim is working. In reality it seems they don't support token auth, but that's how I started out. ``` import base64 import requests nl = "\n" baseUrl = "https://[fqdnWithProperSSL.com]/[appServerWithBasicAuth]/" apiKey = "anAPIKeyYouGenerated" uName = "userNameWithAccesScope" pwd = "YourPassword" string_to_encode = uName + ":" + pwd creds = base64.b64encode(string_to_encode.encode('utf-8')).decode('utf-8') def doToken(): try: svcUrl = baseUrl + "TokenResource.svc" headers = { "Authorization": "Basic " + creds } response = requests.post(svcUrl, headers=headers) data = response.json() for i in data: if i == "AccessToken": brTkn = str(data[i]) except Exception as e: print("Tkn Err " + str(e)) finally: return brTkn def getVendGrp(): try: tkn = doToken() res = "" headers = { "Authorization": "Bearer " + tkn, "x-api-key": apiKey } svcUrl = baseUrl + "api/v2/odata/[Company] /Erp.BO.VendGrupSvc/VendGrups" response = requests.get(svcUrl,headers=headers) data = response.json() for i in data: if str(i) == "value": thing = data[i] for d in thing: res += d["GroupCode"] + " : " + d["GroupDesc"] + nl except Exception as e: print("VGrup Error " + str(e)) finally: return res print(getVendGrp()) ``` This prints out the contents of our vendor groups table, needed because the Vendor object only contains the GroupCode and we have to look it up. Py3 on my phone, just in case anyone mistakes me for someone with a life ![image|382x500](upload://oGSQT3CTLkrbm2bea37eLcLNFtY.png) ------------------------- SteveFossey | 2023-09-08 01:09:40 UTC | #2 Okay, so just for :poop: and :face_with_hand_over_mouth: I also play with Odoo and I still think Epicor needs to watch out for the new guy, but holy cow I'll never complain about Epicor's API again. I am a newcomer to APIs (heck I first met them 2 years ago, on the job) but I was spoiled by REST. I'm sure everyone else here grew through the various iterations - even young guys like @klincecum - but I had never heard of remote procedure calls or the hellish architecture they involve. Anyways, a lot of trial and error and ChatGPT later, I get it. But Epicor API and architecture wins, hands down. Here's my playing around with Odoo RPC just for the fun of it: ``` import requests import xmlrpc.client import json url = "http://[myInstance].odoo.com" db = "myPostGreSQLDB" usr = "myUser" pwd = "myPassword" nl = "\n" api = "/xmlrpc/2/" rslt = "" info = "" try: # get the valid uid of an authenticated API user common = xmlrpc.client.ServerProxy('{}/xmlrpc/2/common'.format(url)) uid = common.authenticate(db, usr, pwd, {}) # set up the ServerProxy models = xmlrpc.client.ServerProxy('{}/xmlrpc/2/object'.format(url)) # check access to the object ("partner" in this case) access_check = models.execute_kw \ (db, uid, pwd, 'res.partner', 'check_access_rights',\ ['read'], {'raise_exception': False}) if access_check == True: # get the ids of partner objects that only are companies ids = models.execute_kw(db, uid, pwd, 'res.partner', \ 'search', [[['is_company','=', True]]]) # get the fields shown that match the ids rslt = json.dumps(models.execute_kw (db, uid, pwd, 'res.partner', \ 'read', [ids], {'fields': ['name', 'phone']}),indent=1) data = json.loads(rslt) for i in data: info += i["name"] + nl else: raise Exception("Model not accessible") except Exception as e: rslt += "except: " + str(e) + nl finally: print(info) ``` This gives me a list of companies, but there's no swagger page, no documentation, and some of the results can be indexed while some cannot... All in all, quite a challenge. Lot's of fun though, and posted just because I'm helping someone sync odoo point of sale with Epicor. Output: ![Screenshot_20230907-205521_Pydroid 3|690x408](upload://xbIHBGzdA3DEgkGD6V585Dmneub.jpeg) -------------------------