Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

2FA Support #85

Open
caboose014 opened this issue Mar 29, 2024 · 2 comments
Open

2FA Support #85

caboose014 opened this issue Mar 29, 2024 · 2 comments

Comments

@caboose014
Copy link

caboose014 commented Mar 29, 2024

I have figured out what needs to be done for the 2FA changes that are coming into effect in July 22nd '24.

Here is the section of code I modified for the login to allow the passing of the 2FA token:

def _login(self):
        self.log.debug("login() as %s", self.username)
        self.session = requests.Session()
        self.session.verify = self.ssl_verify

        response = self.session.post(
            self.auth_url,
            data=json.dumps({"username": self.username, "password": self.password, "ubic_2fa_token": self.token}),
            headers=self.headers,
        )

        print(response.content)

        if response.headers.get("X-CSRF-Token"):
            self.headers = {"X-CSRF-Token": response.headers["X-CSRF-Token"]}
        if response.status_code == 400:
            raise APIError(
                "Login failed - status code: %i, msg: %s" % (response.status_code, response.json()["meta"]["msg"])
                )

        if response.status_code != 200:
            raise APIError(
                "Login failed - status code: %i, msg: %s" % (response.status_code, response.text)
                )

I pass this to the controller using this:

mfa_token = input("Enter your 2FA Token: ")

c = Controller('-Unifi Controller-', '-username-', '-password-', mfa_token)

You also need to add token=0 to the start of the init definition, I put this after the password entry, then you'll need to define the self variable down further using self.token = token

Passing json in the session.post command was not sending in the correct format for this. it needs to be sent as data, and decoded from JSON. I have checked that this still does work with accounts without the 2FA enabled on it, you can either just not pass the 2FA argument, or send any value you like - it will be ignored.

Hope this helps those looking for an answer for this!

@jhavens12
Copy link

Hi thanks for this - one of my controllers (UDM SE) does not ask for a MFA code each time I run the unmodified script, but my other controller (Unifi Express) fails to log in and I get the pop up on my unifi MFA app asking to approve login - which I do, but it obviously doesn't work.

I updated the file as you have above and installed it, but do not understand how to not put in the MFA code each time the script is run. Can you post an example? I'm just trying to run something basic like printing the connected client's IPs.

Thanks

@caboose014
Copy link
Author

Hi jhavens12,

The following bit of code prompts you for your 6 digit code that gets generated by your authentication app:

mfa_token = input("Enter your 2FA Token: ")

Once you type in your code, the script will continue. This is how its setup from what I have written, as I do not have my accounts prompting for authentication prompts via the app - only though an authenticator app.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants