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

glynnbird pushed a commit to branch fix-basicauth-percent-encoding
in repository https://gitbox.apache.org/repos/asf/couchdb-nano.git

commit eb82c2601d8572903f5c96bdecfeb0f33119c8f5
Author: Glynn Bird <[email protected]>
AuthorDate: Fri Feb 6 10:22:43 2026 +0000

    ensure that username and password returned from new URL are decoded before 
use
---
 lib/nano.js                 |  2 +-
 test/nano.basicauth.test.js | 36 ++++++++++++++++++++++++++++++++++++
 2 files changed, 37 insertions(+), 1 deletion(-)

diff --git a/lib/nano.js b/lib/nano.js
index f21389a..ad5dfda 100644
--- a/lib/nano.js
+++ b/lib/nano.js
@@ -56,7 +56,7 @@ module.exports = exports = function dbScope (cfg) {
   cfg.plainURL = `${cfg.parsedURL.origin}${cfg.parsedURL.pathname}`
   cfg.headers = cfg.headers || {}
   if (cfg.parsedURL.username && cfg.parsedURL.password) {
-    cfg.headers.Authorization = 'Basic ' + 
Buffer.from(`${cfg.parsedURL.username}:${cfg.parsedURL.password}`).toString('base64')
+    cfg.headers.Authorization = 'Basic ' + 
Buffer.from(`${decodeURIComponent(cfg.parsedURL.username)}:${decodeURIComponent(cfg.parsedURL.password)}`).toString('base64')
   }
 
   // look for agentOptions
diff --git a/test/nano.basicauth.test.js b/test/nano.basicauth.test.js
new file mode 100644
index 0000000..30a3b9d
--- /dev/null
+++ b/test/nano.basicauth.test.js
@@ -0,0 +1,36 @@
+// Licensed under the Apache License, Version 2.0 (the 'License'); you may not
+// use this file except in compliance with the License. You may obtain a copy 
of
+// the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT
+// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+// License for the specific language governing permissions and limitations 
under
+// the License.
+
+const test = require('node:test')
+const assert = require('node:assert/strict')
+const COUCH_URL="http://admin[:admin]@localhost:5984";
+const { mockAgent, mockPool, JSON_HEADERS } = require('./mock.js')
+const Nano = require('..')
+const nano = Nano(COUCH_URL)
+
+test('should handle special characters in username & password', async () => {
+  // mocks
+  const auth = 'Basic ' + Buffer.from('admin[:admin]').toString('base64')
+  mockPool
+    .intercept({
+      path: '/_all_dbs',
+      headers: {
+        'Authorization': auth
+      }
+    })
+    .reply(200, ['a'], JSON_HEADERS)
+
+  // test POST /_session
+  const q = await nano.db.list()
+  assert.deepEqual(q, ['a'])
+  mockAgent.assertNoPendingInterceptors()
+})

Reply via email to