robweber / xbmcbackup

Backup Addon for Kodi
MIT License
112 stars 48 forks source link

Suggestion For Enhancement: Allow user to auth from an OAuth2 token. #234

Open rjclark99 opened 5 months ago

rjclark99 commented 5 months ago

I'm currently working on an extra settings option which will copy an OAuth2 token and paste it into the appropriate directory in order to simplify the authorisation process if a user already has a valid token they'd like to use.

Looking at the code there should only need to be minor additions and no modification to the base code. I'll simply add a function to handle the token copying process and add an appropriate menu option. From looking at when authorisation occurs, everything should work without any issues.

Before I dive into this I'd just like to know if it is something you would like to have incorporated into the main branch, as if so I will allow the user to select a location instead of just setting a default folder where tokens are copied from.

Pull request for whitespace stripping has been sent as well.

Thanks again for the great add-on, I've only been doing programming for around 6 months and it's been a fantastic learning experience :)

robweber commented 5 months ago

That sounds interesting - can you outline the use case? Right now the token file is specific to this addon (the .json file). Will these changes allow someone to select a different token file?

Making the process easier is always a good goal so if you can get it to work I'd certainly consider adding it in the main branch.

rjclark99 commented 5 months ago

Yes so essentially all the function I'm looking to implement will do is allow the user to navigate to an auth token already generated from this app. In my case I have several devices connected to my home network and found it easier to simply FTP/adbLink the token to the correct directory for my other devices instead of having to through the entire auth process. Would be simpler if the user could select a token file from a local or network folder. Just a nice option for those whose devices need to reauth regularly or are restoring on a compatible new device. Also handy for if sharing a build as no credentials need to be shared.

Reading through the OAuth2 section in the Dropbox API docs confirms that it is in fact normal as the token generated is sufficient to grant access to the app without use of a key or secret.

Option would be in the Remote Dir panel, clicking the option will open an xbmc browse dialog box so the user can navigate to a locally stored auth token that will be copied to the xbmc.backup addon_data folder where the token is normally stored. In order to minimise interaction with other parts of the code I would probably leave the actual authorisation of the token alone completely, trusting the user to supply a valid token and leave your code to function completely as normal during restore/backup as from what I can see auth takes point here anyway.

Sorry if I've not been very clear or have made any incorrect assumptions, this is my first time collaborating on anything and working from someone else's code.

robweber commented 5 months ago

I think that sounds like a great idea. Looking through the current code briefly I did notice that when creating the client in the vfs.py file the App Key and Secret are used to initialize everything. Even with re-using a token it would appear both those values will need to be in the settings as well. I guess testing will tell though.

rjclark99 commented 5 months ago

I’ll definitely check that out, thank you. It does seem from dropbox’s api that the refresh token included in the token.json should be sufficient for credentials for re-authorisation, I will do some testing tonight and try to identify any potential bugs or issues. EDIT: Both App Key and Secret are just initialised as empty strings in the vfs.py, they don't seem to be used at all. I know Dropbox Authoriser in authorizers.py uses them for the flow however it appears that when the Dropbox VFS is first run it checks if the user is already authorised using the _getToken method from the authoriser, which seems to simply check whether a token.json is present and then attempts to use that for authorisation.

The app key and secret seem to be stored server side and are never exposed to the client, by the looks of things they are simply used to start the OAuth2 Flow, subsequent calls with the token (as long as it is valid) are enough to identify the app and permissions granted. Obviously from a security point of view this would not be ideal as a stolen token could be used to make calls to the API, however this use case of this is primarily for people who have multiple devices on the same network and want to share an OAuth2 Token to prevent authorising every device individually.

rjclark99 commented 5 months ago

Because of how the OAuth2 tokens work with refresh tokens, this is going to be significantly harder to implement than I first thought. I am still going to look into creating an implementation for this however it will involve using a centralised token management system in which every time a device connects to the api the latest token is grabbed, used for auth and the token is refreshed, the new token is stored for the next api call. I'm going to do some research on AWS Secrets Manager and similar tools to see if this can be managed through their APIs.

If you have Discord or another messaging service and you are available to discuss I'd love to get your input on design as after all it is your add-on and I'd like to ensure you are happy with the result should you choose to incorporate it into the main branch.

robweber commented 5 months ago

Having to set up some kind of infrastructure to make this work seems like a heavy lift for the average user. Most people would probably just go the route of authorizing another client. It's kind of the path of least resistance at that point given that you'd have to have a mechanism to set up and authorize them on whatever key management system they'd be using. Kind of like jumping through the same hoop.

Could you piece together some kind of proof of concept and point me to the branch you're working off of? Maybe that would shed more light on the flow here.

rjclark99 commented 4 months ago

Yes upon review I agree, apologies for the delay in response. I imagine the best way to achieve what I'm discussing would be to simply host the zip backup somewhere which doesn't require auth and simply download manually and point Backup to the zip as is already implemented.