Code Monkey home page Code Monkey logo

pymonzo's Introduction

Hi.

My name is Paweล‚, and I'm a developer that uses Python to create stuff.

Some of the projects I created:

  • pymonzo - Modern Python API client for Monzo public API.
  • monz - Simple CLI for your Monzo account.
  • fakester - Rickroll your boss while preserving the element of surprise.

Some of the projects I contributed to:
pytest, tox, celery, errbot, mattermost, django-polymorphic, django-organizations, django-reversion, django-kronos

Some other things:

pymonzo's People

Contributors

bartonp avatar csogilvie avatar pawelad avatar sheaffy avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar

pymonzo's Issues

Initial setup of OAuth as in README is broken

When using the python interpreter to set up OAuth as suggested in the README, it fails because:

  • MonzoAPI._token is set in MonzoAPI.__init__ by calling self_get_oauth_token()
  • This calls self._save_token_on_disk() before returning
  • _save _token_on_disk() tries to do token = self._token.copy(), but fails with AttributeError: 'MonzoAPI' object has no attribute '_token' becasue _token isn't set yet because _get_oauth_token() has not yet returned.

Monzo API HTTP 401 response didn't trigger token refreshing

There was a use case where the reauth wasn't doing the required actions. I added my own checks in to see what was happening. The response code from the server was 401 which means you are unauthorised. Upon this error, it was also failing to re-authenticate. The error codes can be seen in the documentation here - https://monzo.com/docs/#errors.

If I run across the error again, I'll get some more debugging information added in to see what is actually happening in the long term.

Minimal code snippet below to see when it was happening:

from ConfigParser import ConfigParser
import pymonzo

conf = ConfigParser()
conf.read('api_info.conf')
data = dict(conf.items('monzo'))

api = pymonzo.MonzoAPI(client_id=data['client_id'], client_secret=data['client_secret'])

Invalid Redirect URI

When MonzoAPI() is called with keyword arguments (i.e. not using env variables) I get the following response:

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python2.7/dist-packages/pymonzo/monzo_api.py", line 76, in __init__
    self._token = self._get_oauth_token()
  File "/usr/local/lib/python2.7/dist-packages/pymonzo/monzo_api.py", line 155, in _get_oauth_token
    client_secret=self._client_secret,
  File "/usr/local/lib/python2.7/dist-packages/requests_oauthlib/oauth2_session.py", line 244, in fetch_token
    self._client.parse_request_body_response(r.text, scope=self.scope)
  File "/usr/local/lib/python2.7/dist-packages/oauthlib/oauth2/rfc6749/clients/base.py", line 411, in parse_request_body_response
    self.token = parse_token_response(body, scope=scope)
  File "/usr/local/lib/python2.7/dist-packages/oauthlib/oauth2/rfc6749/parameters.py", line 379, in parse_token_response
    validate_token_parameters(params)
  File "/usr/local/lib/python2.7/dist-packages/oauthlib/oauth2/rfc6749/parameters.py", line 386, in validate_token_parameters
    raise_from_error(params.get('error'), params)
  File "/usr/local/lib/python2.7/dist-packages/oauthlib/oauth2/rfc6749/errors.py", line 415, in raise_from_error
    raise cls(**kwargs)
oauthlib.oauth2.rfc6749.errors.InvalidClientIdError: (invalid_request) Invalid redirect URI

I'm assuming this is to do with how I have configured the client on the Monzo dev portal, but I can't see what's wrong with it?

Unable to access the Monzo API when running as root on raspberry pi 3

Hello everyone,

I have managed to set up the API access following all the instructions in the readme, saving the client ID, client secret and auth code in the auth.py file. The codes work when I run them normally, i.e. python3 filename.py, and I can obtain my transaction data, balance, etc. with no problem.

However, I am also using the Adafruit Neopixel library to control some LED lights at the same time. The library can be found here: https://github.com/adafruit/Adafruit_NeoPixel

Using this library apparently has two constraints: it has to be run in Python 3, and it has to be run as root. The documentation explains that "For NeoPixels to work on Raspberry Pi, you must run the code as root! Root access is required to access the RPi peripherals." Further documentation can be found here: https://cdn-learn.adafruit.com/downloads/pdf/neopixels-on-raspberry-pi.pdf

The problem is, I can't seem to run the PyMonzo codes when I run as root (i.e. sudo python3 filename.py). The error I get is:
Traceback (most recent call last):
File "filename.py", line 34, in
monzo = MonzoAPI( )
File "/usr/local/lib/python3.5/dist-packages/pymonzo/monzo_api.py", line 106, in init
"To authenticate and use Monzo public API you need to pass "
ValueError: To authenticate and use Monzo public API you need to pass (or set as environment variables either the access token or all of client ID, client secret and authentication code. For more info see https://github.com/pawelad/pymonzo#authentication

If I run the code normally without using sudo, the error I get is:
Can't open /dev/mem: Operation not permitted
Traceback (most recent call last):
File "filename.py", line 66, in
neopix.show( )
.....
RuntimeError: ws2811_init failed with code -5 (mmap( ) failed)
swig/python detected a memory leak of type 'ws2811_t *', no destructor found

Does anyone know if there is a way to deconflict between these two operations, perhaps a way that pyMonzo can be run as root?

I have tried running sudo chmod 666 /dev/mem, and running it without sudo.

Thank you very much.

I can't authenticate with OAuth 2 - 'oauthlib.oauth2.rfc6749.errors.ServerError'

I am getting errors when running the MonzoAPI() command after exporting the authorisation environment variables.

Also it is not clear from where I should get the auth code to input. Is the code the whole URL from the email or just the part after 'code='?

Thank you.

m.MonzoAPI()
Traceback (most recent call last):
File "", line 1, in
File "/usr/local/lib/python3.6/site-packages/pymonzo/monzo_api.py", line 95, in init
self._token = self._get_oauth_token()
File "/usr/local/lib/python3.6/site-packages/pymonzo/monzo_api.py", line 144, in _get_oauth_token
client_secret=self._client_secret,
File "/usr/local/lib/python3.6/site-packages/requests_oauthlib/oauth2_session.py", line 244, in fetch_token
self._client.parse_request_body_response(r.text, scope=self.scope)
File "/usr/local/lib/python3.6/site-packages/oauthlib/oauth2/rfc6749/clients/base.py", line 409, in parse_request_body_response
self.token = parse_token_response(body, scope=scope)
File "/usr/local/lib/python3.6/site-packages/oauthlib/oauth2/rfc6749/parameters.py", line 376, in parse_token_response
validate_token_parameters(params)
File "/usr/local/lib/python3.6/site-packages/oauthlib/oauth2/rfc6749/parameters.py", line 383, in validate_token_parameters
raise_from_error(params.get('error'), params)
File "/usr/local/lib/python3.6/site-packages/oauthlib/oauth2/rfc6749/errors.py", line 404, in raise_from_error
raise cls(**kwargs)
oauthlib.oauth2.rfc6749.errors.ServerError: (server_error) Unknown error occurred

OAuth token refreshing doesn't work

Hi there,

Thanks again for the help with the previous issue.

Is there a way for me to restart my machine and then use MonzoAPI() without getting another Auth_Code for my Client?

Thanks,
Jack

Question: Help with exporting information to CSV

I have this code to export a CSV:

    import csv

from pymonzo import MonzoAPI


if __name__ == '__main__':
    monzo_api = MonzoAPI()
    monzo_transactions = monzo_api.transactions()

    with open('monzo_transactions.csv', 'w') as csvfile:
        writer = csv.writer(csvfile)
        writer.writerow([
                'transaction.amount', 'transaction.description', 'transaction.created',
            ])

        for transaction in monzo_transactions:
            writer.writerow([
                transaction.amount, transaction.description, transaction.created,
            ])

    print('MONZO DATA SAVED!')

I also want to get my balance at the date of the transaction. Really for the purposes of this project all I need are [DATE] and [BALANCE] columns.

I can see that balance is part of the transaction information under 'account_balance' but I can't seem to just add it like with the others in the code.

Any ideas?

I apologise if I should not be putting these questions in the issues section.

Thanks.

ValueError: Passed data doesn't have all required keys (missing keys: created)

pymonzo version: v0.11.0 (latest)

This started happening for me since 15.03.2022:

Stacktrace:

  ...
  File "/app/export.py", line 44, in <genexpr>                                                                                                                                                                                                                
    self.api.transaction(t['id'], expand_merchant=True)._raw_data
  File "/usr/local/lib/python3.8/site-packages/pymonzo/monzo_api.py", line 398, in transaction                                                                                                                                                                
    return MonzoTransaction(data=response.json()['transaction'])                                                                                                                                                                                              
  File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 42, in __init__                                                                                                                                                                  
    self._parse_special_fields(data_copy)                                                                                                                                                                                                                     
  File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 117, in _parse_special_fields                                                                                                                                                    
    self.merchant = MonzoMerchant(data=data.pop('merchant'))                                                                                                                                                                                                  
  File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 33, in __init__                                                                                                                                                                  
    raise ValueError(                                                                                                                                                                                                                                         
ValueError: Passed data doesn't have all required keys (missing keys: created)

More debugging:

DEBUG:requests_oauthlib.oauth2_session:Passing through key word arguments {'params': {'expand[]': 'merchant'}, 'allow_redirects': True}.
DEBUG:urllib3.connectionpool:https://api.monzo.com:443 "GET /transactions/tx_XXXXXXXXXXXXXXX?expand%5B%5D=merchant HTTP/1.1" 200 None
(Pdb) self.api._get_response(method='get', endpoint=f"/transactions/{transactions[0]['id']}", params={'expand[]': 'merchant'}).json()['transaction']['merchant']
{'id': 'merch_0000A7F9qhxKe3RynPV14E', 'group_id': 'grp_000092JZy7UcN7FpKMkvh3', 'name': 'Deliveroo', 'logo': 'https://mondo-logo-cache.appspot.com/twitter/deliveroo/?size=large', 'emoji': '๐Ÿ๐Ÿฆ˜', 'category': 'eating_out', 'online': True, 'atm': False, 'address': {'short_formatted': 'Somewhere in the United Kingdom', 'city': '', 'latitude': 54.557817, 'longitude': -3.484688, 'zoom_level': 4, 'approximate': True, 'formatted': 'United Kingdom', 'address': '', 'region': '', 'country': 'GBR', 'postcode': ''}, 'disable_feedback': False, 'suggested_tags': '#groceries #food, #delivery #yum', 'metadata': {'suggested_tags': '#groceries #food, #delivery #yum', 'website': 'www.deliveroo.co.uk'}

So merchant creation date is missing from the payload. I couldn't find API docs for merchants, so not sure if it's just not passed by the API now

Possibly related: monzo/docs#71

I tried monkey patching it with the following snippet:

M_keys = MonzoMerchant._required_keys                                                                                                                                                                                                                     
if 'created' in M_keys:                                                                                                                                                                                                                                   
    M_keys.remove('created')                                                                                                                                                                                                                              

But sadly this fails with, so seems created is hardcoded in pymonzo code

 File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 117, in _parse_special_fields
    self.merchant = MonzoMerchant(data=data.pop('merchant'))
  File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 42, in __init__
    self._parse_special_fields(data_copy)
  File "/usr/local/lib/python3.8/site-packages/pymonzo/api_objects.py", line 136, in _parse_special_fields
    self.created = parse_date(data.pop('created'))
KeyError: 'created`

So I think for now, for my monzoexport, I'll just use the raw __get_response method. But let me know if you're interested in a proper fix, I might come up with some PR. Thanks!

MonzoTransaction object.

Using transaction() is returning [<class 'pymonzo.api_objects.MonzoTransaction'> instead of the expected output MonzoTransaction({data here}) (MonzoTransaction object).

Or is this expected output?

Make MonzoObject serializable to JSON?

I was hoping to be able to do json.dumps(monzoTransaction) but get TypeError(repr(o) + " is not JSON serializable") - I'm working around this, but it would be really handy for the use case I'm working on (a tool to batch-import transactions into YNAB)

'dev' branch?

Hi, just noticed there is a dev branch, that seems more up to date with main. Just wondering if you're ever planning to merge it in main and release? :)

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.