Repository: Backblaze/B2_Command_Line_Tool

Issue:
Please add an option to authorize_account to let me specify a base url.
The goal is to let us run the CLI against other B2 instances without having to change the code to add additional arguments like the "--staging" and "--dev" arguments that currently exist.

Here's a potential example:

   b2 authorize-account --baseUrl https://api.backblazeb2.xyz

thanks,
ab


Discussion:

Patch:
diff --git a/README.md b/README.md
index beaabdc..727ae51 100644
--- a/README.md
+++ b/README.md
@@ -108,6 +108,10 @@ For advanced users, a hidden option `--logConfig <filename.ini>` can be used to
 
 # Release History
 
+## Not released yet
+
+* Add `--environment` internal parameter for `authorize-account`
+
 ## 2.0.0 (2020-06-25)
 
 Changes:
diff --git a/b2/console_tool.py b/b2/console_tool.py
index 2914a16..867a205 100644
--- a/b2/console_tool.py
+++ b/b2/console_tool.py
@@ -283,21 +283,20 @@ class AuthorizeAccount(Command):
 
     @classmethod
     def _setup_parser(cls, parser):
-        parser.add_argument('--dev', action='store_true', help=argparse.SUPPRESS)
-        parser.add_argument('--staging', action='store_true', help=argparse.SUPPRESS)
+        realm_group = parser.add_mutually_exclusive_group()
+        realm_group.add_argument('--dev', action='store_true', help=argparse.SUPPRESS)
+        realm_group.add_argument('--staging', action='store_true', help=argparse.SUPPRESS)
+        realm_group.add_argument('--environment', help=argparse.SUPPRESS)
+
         parser.add_argument('applicationKeyId', nargs='?')
         parser.add_argument('applicationKey', nargs='?')
 
     def run(self, args):
-        # Handle internal options for testing inside Backblaze.  These
-        # are not documented in the usage string.
-        realm = 'production'
-        if args.staging:
-            realm = 'staging'
-        if args.dev:
-            realm = 'dev'
+        # Handle internal options for testing inside Backblaze.
+        # These are not documented in the usage string.
+        realm = self._get_realm(args)
 
-        url = self.api.account_info.REALM_URLS[realm]
+        url = self.api.account_info.REALM_URLS.get(realm, realm)
         self._print('Using %s' % url)
 
         if args.applicationKeyId is None:
@@ -339,6 +338,17 @@ class AuthorizeAccount(Command):
             self._print_stderr('ERROR: unable to authorize account: ' + str(e))
             return 1
 
+    @classmethod
+    def _get_realm(cls, args):
+        if args.dev:
+            return 'dev'
+        if args.staging:
+            return 'staging'
+        if args.environment:
+            return args.environment
+
+        return 'production'
+
 
 @B2.register_subcommand
 class CancelAllUnfinishedLargeFiles(Command):
diff --git a/requirements.txt b/requirements.txt
index b1235a4..1006adb 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -1,5 +1,5 @@
 arrow>=0.8.0,<0.13.1; python_version <= '3.4'
 arrow>=0.8.0; python_version > '3.4'
-b2sdk>=1.1.0,<1.2.0
+b2sdk>=1.1.3,<1.2.0
 class-registry==2.1.2
 six>=1.13


Test patch:
diff --git a/test/test_console_tool.py b/test/test_console_tool.py
index 8956eec..4e7f652 100644
--- a/test/test_console_tool.py
+++ b/test/test_console_tool.py
@@ -110,6 +110,25 @@ class TestConsoleTool(TestBase):
         # Auth token should be in account info now
         assert self.account_info.get_account_auth_token() is not None
 
+    def test_authorize_towards_custom_realm(self):
+        # Initial condition
+        assert self.account_info.get_account_auth_token() is None
+
+        # Authorize an account with a good api key.
+        expected_stdout = """
+        Using http://custom.example.com
+        """
+
+        self._run_command(
+            [
+                'authorize-account', '--environment', 'http://custom.example.com', self.account_id,
+                self.master_key
+            ], expected_stdout, '', 0
+        )
+
+        # Auth token should be in account info now
+        assert self.account_info.get_account_auth_token() is not None
+
     def test_create_key_and_authorize_with_it(self):
         # Start with authorizing with the master key
         self._authorize_account()