You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@apisix.apache.org by mo...@apache.org on 2023/04/10 14:31:20 UTC

[apisix] branch master updated: feat(cli): support bypassing Admin API Auth by configuration (#9147)

This is an automated email from the ASF dual-hosted git repository.

monkeydluffy pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/apisix.git


The following commit(s) were added to refs/heads/master by this push:
     new 2c5639bf0 feat(cli): support bypassing Admin API Auth by configuration (#9147)
2c5639bf0 is described below

commit 2c5639bf05bae67d29e4c755b3b98ae3abd2ec6f
Author: dongjunduo <an...@gmail.com>
AuthorDate: Mon Apr 10 22:31:13 2023 +0800

    feat(cli): support bypassing Admin API Auth by configuration (#9147)
---
 apisix/admin/init.lua    | 13 ++++++++
 apisix/cli/ops.lua       |  7 +++++
 apisix/cli/schema.lua    |  3 ++
 conf/config-default.yaml |  4 +++
 t/admin/api.t            | 80 ++++++++++++++++++++++++++++++++++++++++++++++++
 t/cli/test_admin.sh      | 56 +++++++++++++++++++++++++++++++++
 6 files changed, 163 insertions(+)

diff --git a/apisix/admin/init.lua b/apisix/admin/init.lua
index 072a58435..ccea011fe 100644
--- a/apisix/admin/init.lua
+++ b/apisix/admin/init.lua
@@ -67,6 +67,12 @@ local router
 
 local function check_token(ctx)
     local local_conf = core.config.local_conf()
+
+    -- check if admin_key is required
+    if local_conf.deployment.admin.admin_key_required == false then
+        return true
+    end
+
     local admin_key = core.table.try_read_attr(local_conf, "deployment", "admin", "admin_key")
     if not admin_key then
         return true
@@ -395,6 +401,13 @@ function _M.init_worker()
     events.register(reload_plugins, reload_event, "PUT")
 
     if ngx_worker_id() == 0 then
+        -- check if admin_key is required
+        if local_conf.deployment.admin.admin_key_required == false then
+            core.log.warn("Admin key is bypassed! ",
+                "If you are deploying APISIX in a production environment, ",
+                "please disable `admin_key_required` and set a secure admin key!")
+        end
+
         local ok, err = ngx_timer_at(0, function(premature)
             if premature then
                 return
diff --git a/apisix/cli/ops.lua b/apisix/cli/ops.lua
index 5ce51dab3..ebd3061e0 100644
--- a/apisix/cli/ops.lua
+++ b/apisix/cli/ops.lua
@@ -189,6 +189,13 @@ local function init(env)
        and #allow_admin == 1 and allow_admin[1] == "127.0.0.0/24" then
         checked_admin_key = true
     end
+    -- check if admin_key is required
+    if yaml_conf.deployment.admin.admin_key_required == false then
+        checked_admin_key = true
+        print("Warning! Admin key is bypassed! "
+                .. "If you are deploying APISIX in a production environment, "
+                .. "please disable `admin_key_required` and set a secure admin key!")
+    end
 
     if yaml_conf.apisix.enable_admin and not checked_admin_key then
         local help = [[
diff --git a/apisix/cli/schema.lua b/apisix/cli/schema.lua
index 477e2ce7e..56d7e2f63 100644
--- a/apisix/cli/schema.lua
+++ b/apisix/cli/schema.lua
@@ -353,6 +353,9 @@ local admin_schema = {
         https_admin = {
             type = "boolean",
         },
+        admin_key_required = {
+            type = "boolean",
+        },
     }
 }
 
diff --git a/conf/config-default.yaml b/conf/config-default.yaml
index 2765afe9c..d61f745af 100755
--- a/conf/config-default.yaml
+++ b/conf/config-default.yaml
@@ -588,6 +588,10 @@ deployment:
   role_traditional:
     config_provider: etcd
   admin:
+    # Admin API authentication is enabled by default.
+    # Set it false in the production environment will cause a serious security issue.
+    # admin_key_required: true
+
     # Default token when use API to call for Admin API.
     # *NOTE*: Highly recommended to modify this value to protect APISIX's Admin API.
     # Disabling this configuration item means that the Admin API does not
diff --git a/t/admin/api.t b/t/admin/api.t
index 67d7344b6..982becc79 100644
--- a/t/admin/api.t
+++ b/t/admin/api.t
@@ -156,3 +156,83 @@ X-API-VERSION: v2
 GET /t
 --- response_body
 passed
+
+
+
+=== TEST 10: Access with api key, and admin_key_required=true
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: true
+--- more_headers
+X-API-KEY: edd1c9f034335f136f87ad84b625c8f1
+--- request
+GET /apisix/admin/routes
+--- error_code: 200
+
+
+
+=== TEST 11: Access with wrong api key, and admin_key_required=true
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: true
+--- more_headers
+X-API-KEY: wrong-key
+--- request
+GET /apisix/admin/routes
+--- error_code: 401
+
+
+
+=== TEST 12: Access without api key, and admin_key_required=true
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: true
+--- request
+GET /apisix/admin/routes
+--- error_code: 401
+
+
+
+=== TEST 13: Access with api key, but admin_key_required=false
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: false
+--- more_headers
+X-API-KEY: edd1c9f034335f136f87ad84b625c8f1
+--- request
+GET /apisix/admin/routes
+--- error_code: 200
+--- error_log
+Admin key is bypassed!
+
+
+
+=== TEST 14: Access with wrong api key, but admin_key_required=false
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: false
+--- more_headers
+X-API-KEY: wrong-key
+--- request
+GET /apisix/admin/routes
+--- error_code: 200
+--- error_log
+Admin key is bypassed!
+
+
+
+=== TEST 15: Access without api key, but admin_key_required=false
+--- yaml_config
+deployment:
+  admin:
+    admin_key_required: false
+--- request
+GET /apisix/admin/routes
+--- error_code: 200
+--- error_log
+Admin key is bypassed!
diff --git a/t/cli/test_admin.sh b/t/cli/test_admin.sh
index 6f39ffae1..aad049728 100755
--- a/t/cli/test_admin.sh
+++ b/t/cli/test_admin.sh
@@ -189,6 +189,62 @@ fi
 
 echo "pass: missing admin key and only allow 127.0.0.0/24 to access admin api"
 
+# allow any IP to access admin api with empty admin_key, when admin_key_required=true
+
+git checkout conf/config.yaml
+
+echo '
+deployment:
+  admin:
+    admin_key_required: true
+    admin_key: ~
+    allow_admin:
+      - 0.0.0.0/0
+' > conf/config.yaml
+
+make init > output.log 2>&1 | true
+
+if ! grep -E "ERROR: missing valid Admin API token." output.log > /dev/null; then
+    echo "failed: should show 'ERROR: missing valid Admin API token.'"
+    exit 1
+fi
+
+echo '
+deployment:
+  admin:
+    admin_key_required: false
+    admin_key: ~
+    allow_admin:
+      - 0.0.0.0/0
+' > conf/config.yaml
+
+make init > output.log 2>&1 | true
+
+if grep -E "ERROR: missing valid Admin API token." output.log > /dev/null; then
+    echo "failed: should not show 'ERROR: missing valid Admin API token.'"
+    exit 1
+fi
+
+if ! grep -E "Warning! Admin key is bypassed" output.log > /dev/null; then
+    echo "failed: should show 'Warning! Admin key is bypassed'"
+    exit 1
+fi
+
+echo '
+deployment:
+  admin:
+    admin_key_required: invalid-value
+' > conf/config.yaml
+
+make init > output.log 2>&1 | true
+
+if grep -E "path[deployment->admin->admin_key_required] expect: boolean, but got: string" output.log > /dev/null; then
+    echo "check admin_key_required value failed: should show 'expect: boolean, but got: string'"
+    exit 1
+fi
+
+echo "pass: allow empty admin_key, when admin_key_required=false"
+
 # admin api, allow any IP but use default key
 
 echo '