// 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 { URL } = require('url')
const http = require('http')
const https = require('https')
const assert = require('assert')
const querystring = require('qs')
const axios = require('axios')
const stream = require('stream')
const pkg = require('../package.json')
const AGENT_DEFAULTS = { keepAlive: true, maxSockets: 50, keepAliveMsecs: 30000 }
const defaultHttpAgent = new http.Agent(AGENT_DEFAULTS)
const defaultHttpsAgent = new https.Agent(AGENT_DEFAULTS)
const SCRUBBED_STR = 'XXXXXX'
const ChangesReader = require('./changesreader.js')
const CookieJar = require('./cookie.js')
const MultiPartFactory = require('./multipart.js')

function isEmpty (val) {
  return val == null || !(Object.keys(val) || val).length
}

function getCallback (opts, callback) {
  if (typeof opts === 'function') {
    callback = opts
    opts = {}
  }
  opts = opts || {}
  return {
    opts,
    callback
  }
}

// feed this any number of arguements, it will return true if
// any of them are missing (falsey)
function missing (...params) {
  return params.some(param => !param)
}

// calls the supplied callback or if not supplied, returns a rejected promise
function callbackOrRejectError (callback, error = new Error('Invalid parameters')) {
  if (callback) {
    return callback(error, null)
  } else {
    return Promise.reject(error)
  }
}

module.exports = exports = function dbScope (cfg) {
  let serverScope = {}

  if (typeof cfg === 'string') {
    cfg = { url: cfg }
  }

  assert.strictEqual(typeof cfg, 'object',
    'You must specify the endpoint url when invoking this module')
  assert.ok(/^https?:/.test(cfg.url), 'url is not valid')

  cfg = Object.assign({}, cfg)

  serverScope.config = cfg
  cfg.requestDefaults = cfg.requestDefaults || {}

  const dummyLogger = () => {}
  const log = typeof cfg.log === 'function' ? cfg.log : dummyLogger
  const parseUrl = 'parseUrl' in cfg ? cfg.parseUrl : true

  // create cookieJar for this Nano
  cfg.cookieJar = new CookieJar()

  function maybeExtractDatabaseComponent () {
    if (!parseUrl) {
      return
    }

    const path = new URL(cfg.url)
    const pathArray = path.pathname.split('/').filter(function (e) { return e })
    const db = pathArray.pop()
    const rootPath = path.pathname.replace(/\/?$/, '/..')

    if (db) {
      cfg.url = urlResolveFix(cfg.url, rootPath).replace(/\/?$/, '')
      return db
    }
  }

  function scrubURL (str) {
    if (str) {
      str = str.replace(/\/\/(.*)@/, `//${SCRUBBED_STR}:${SCRUBBED_STR}@`)
    }
    return str
  }

  function scrubRequest (req, cloned) {
    // scrub credentials
    req.url = scrubURL(req.url)
    if (req.headers.cookie) {
      req.headers.cookie = 'XXXXXXX'
    }
    if (req.auth) {
      if (!cloned) {
        req.auth = JSON.parse(JSON.stringify(req.auth)) // clone just auth if not already cloned
      }
      req.auth.username = SCRUBBED_STR
      req.auth.password = SCRUBBED_STR
    }
  }

  const responseHandler = function (response, req, opts, resolve, reject, callback) {
    const statusCode = response.status || (response.response && response.response.status) || 500
    if (response.isAxiosError && response.response) {
      response = response.response
    }
    let body = response.data
    response.statusCode = statusCode

    // cookie parsing
    if (response.headers) {
      const h = response.headers['set-cookie']
      if (h && h.length) {
        h.forEach((header) => {
          cfg.cookieJar.parse(header, req.url)
        })
      }
    }

    // let parsed
    const responseHeaders = Object.assign({
      uri: scrubURL(req.url),
      statusCode
    }, response.headers)
    if (!response.status) {
      if (axios.isCancel(response)) {
        if (resolve) {
          resolve('canceled')
        }
        if (callback) {
          callback(null, 'canceled', responseHeaders)
        }
        return
      }

      log({ err: 'socket', body, headers: responseHeaders })
      if (reject) {
        reject(new Error(`error happened in your connection. Reason: ${response.message}`))
      }
      if (callback) {
        const returnError = new Error(`error happened in your connection. Reason: ${response.message}`)
        returnError.scope = 'socket'
        returnError.errid = 'request'
        callback(returnError)
      }
      return
    }

    delete responseHeaders.server
    delete responseHeaders['content-length']

    /* if (opts.dontParse) {
      parsed = body
    } else {
      try { parsed = JSON.parse(body) } catch (err) { parsed = body }
    } */

    if (statusCode >= 200 && statusCode < 400) {
      log({ err: null, body, headers: responseHeaders })
      if (resolve) {
        resolve(body)
      }
      if (callback) {
        callback(null, body, responseHeaders)
      }
      return
    }

    // cloudant stacktrace
    if (typeof body === 'string') {
      body = { message: body }
    }

    if (!body.message && (body.reason || body.error)) {
      body.message = (body.reason || body.error)
    }

    // fix cloudant issues where they give an erlang stacktrace as js
    delete body.stack

    // scrub credentials
    scrubRequest(req)

    log({ err: 'couch', body, headers: responseHeaders })

    const message = body.message || 'couch returned ' + statusCode
    const errors = new Error(message)
    errors.scope = 'couch'
    errors.statusCode = statusCode
    errors.request = req
    errors.headers = responseHeaders
    errors.errid = 'non_200'
    errors.name = 'Error'
    errors.description = message
    // add any attributes from the HTTP response into the
    // Error object (except message, which would overwrite
    // the text message of the Error)
    delete body.message
    Object.assign(errors, body)

    if (reject) {
      reject(errors)
    }
    if (callback) {
      callback(errors)
    }
  }

  const streamResponseHandler = function (response, req, stream) {
    const statusCode = response.status || (response.response && response.response.status) || 500
    if (response.isAxiosError && response.response) {
      response = response.response
    }
    const message = response.statusText

    scrubRequest(req)

    const responseHeaders = Object.assign({
      uri: req.url,
      statusCode
    }, response.headers)

    const error = new Error(message)
    error.scope = 'couch'
    error.statusCode = statusCode
    error.request = req
    error.headers = responseHeaders
    error.errid = 'non_200'
    error.name = 'Error'
    error.description = message
    error.reason = message

    log({ err: 'couch', body: message, headers: responseHeaders })

    stream.emit('error', error)
  }

  function relax (opts, callback) {
    if (typeof opts === 'function') {
      callback = opts
      opts = { path: '' }
    }

    if (typeof opts === 'string') {
      opts = { path: opts }
    }

    if (!opts) {
      opts = { path: '' }
      callback = null
    }

    const qs = Object.assign({}, opts.qs)

    const headers = {
      'content-type': 'application/json',
      accept: 'application/json',
      'user-agent': `${pkg.name}/${pkg.version} (Node.js ${process.version})`,
      'Accept-Encoding': 'deflate, gzip'
    }

    const req = Object.assign({
      method: (opts.method || 'GET'),
      headers,
      uri: cfg.url
    }, {
      ...cfg.requestDefaults,
      headers: Object.assign(headers, cfg.requestDefaults && cfg.requestDefaults.headers ? cfg.requestDefaults.headers : {})
    })

    // https://github.com/mikeal/request#requestjar
    const isJar = opts.jar || cfg.jar || (cfg.requestDefaults && cfg.requestDefaults.jar)

    if (opts.signal) {
      req.signal = opts.signal
    }

    if (isJar) {
      req.withCredentials = true
    }

    // http://wiki.apache.org/couchdb/HTTP_database_API#Naming_and_Addressing
    if (opts.db) {
      req.uri = urlResolveFix(req.uri, encodeURIComponent(opts.db))
    }

    if (opts.multipart) {
      // generate the multipart/related body, header and boundary to
      // upload multiple binary attachments in one request
      const mp = new MultiPartFactory(opts.multipart)
      opts.contentType = mp.header
      req.body = mp.data
    }

    req.headers = Object.assign(req.headers, opts.headers, cfg.defaultHeaders)

    if (opts.path) {
      req.uri += '/' + opts.path
    } else if (opts.doc) {
      if (!/^_design|_local/.test(opts.doc)) {
        // http://wiki.apache.org/couchdb/HTTP_Document_API#Naming.2FAddressing
        req.uri += '/' + encodeURIComponent(opts.doc)
      } else {
        // http://wiki.apache.org/couchdb/HTTP_Document_API#Document_IDs
        req.uri += '/' + opts.doc
      }

      // http://wiki.apache.org/couchdb/HTTP_Document_API#Attachments
      if (opts.att) {
        req.uri += '/' + opts.att
      }
    }

    // prevent bugs where people set encoding when piping
    if (opts.encoding !== undefined) {
      req.encoding = opts.encoding
      delete req.headers['content-type']
      delete req.headers.accept
    }

    if (opts.contentType) {
      req.headers['content-type'] = opts.contentType
      delete req.headers.accept
    }

    if (opts.accept) {
      req.headers.accept = opts.accept
    }

    // http://guide.couchdb.org/draft/security.html#cookies
    if (cfg.cookie) {
      req.headers['X-CouchDB-WWW-Authenticate'] = 'Cookie'
      req.headers.cookie = cfg.cookie
    }

    // http://wiki.apache.org/couchdb/HTTP_view_API#Querying_Options
    if (typeof opts.qs === 'object' && !isEmpty(opts.qs)) {
      ['startkey', 'endkey', 'key', 'keys', 'start_key', 'end_key'].forEach(function (key) {
        if (key in opts.qs) {
          qs[key] = JSON.stringify(opts.qs[key])
        }
      })
      req.qs = qs
    }

    // add any cookies for this domain
    const cookie = cfg.cookieJar.getCookieString(req.uri)
    if (cookie) {
      req.headers.cookie = cookie
    }

    if (opts.body) {
      if (Buffer.isBuffer(opts.body) || opts.dontStringify) {
        req.body = opts.body
      } else {
        req.body = JSON.stringify(opts.body, function (key, value) {
          // don't encode functions
          if (typeof (value) === 'function') {
            return value.toString()
          } else {
            return value
          }
        })
      }
    }

    if (opts.form) {
      req.headers['content-type'] =
        'application/x-www-form-urlencoded; charset=utf-8'
      req.body = querystring.stringify(opts.form).toString('utf8')
    }

    // ask request to render query string arrays as repeated values e.g.
    // ?drilldown=["author","Dickens"]&drilldown=["publisher","Penguin"]
    req.qsStringifyOptions = { arrayFormat: 'repeat' }

    // This where the HTTP request is made.
    // Nano used to use the now-deprecated "request" library but now we're going to
    // use axios, so let's modify the "req" object to suit axios
    req.url = req.uri
    delete req.uri
    req.method = req.method.toLowerCase()
    req.params = req.qs
    delete req.qs
    req.paramsSerializer = {
      serialize: (params) => querystring.stringify(params, { arrayFormat: 'brackets' })
    }
    req.data = req.body
    delete req.body
    req.maxRedirects = 0
    if (opts.stream) {
      req.responseType = 'stream'
    } else if (opts.dontParse) {
      req.responseType = 'arraybuffer'
    }

    // scrub and log
    const scrubbedReq = {
      method: req.method,
      headers: JSON.parse(JSON.stringify(req.headers)),
      url: req.url
    }
    scrubRequest(scrubbedReq, true)
    log(scrubbedReq)

    // add http agents
    req.httpAgent = cfg.requestDefaults.agent || defaultHttpAgent
    req.httpsAgent = cfg.requestDefaults.agent || defaultHttpsAgent
    const ax = axios.create({
      httpAgent: req.httpAgent,
      httpsAgent: req.httpsAgent
    })

    // actually do the HTTP request
    if (opts.stream) {
      // return the Request object for streaming
      const outStream = new stream.PassThrough()
      ax(req)
        .then((response) => {
          response.data.pipe(outStream)
        }).catch(e => {
          streamResponseHandler(e, req, outStream)
        })
      return outStream
    } else {
      if (typeof callback === 'function') {
        ax(req).then((response) => {
          responseHandler(response, req, opts, null, null, callback)
        }).catch((e) => {
          responseHandler(e, req, opts, null, null, callback)
        })
      } else {
        return new Promise((resolve, reject) => {
          ax(req).then((response) => {
            responseHandler(response, req, opts, resolve, reject)
          }).catch((e) => {
            responseHandler(e, req, opts, resolve, reject)
          })
        })
      }
    }
  }

  // http://docs.couchdb.org/en/latest/api/server/authn.html#cookie-authentication
  function auth (username, password, callback) {
    return relax({
      method: 'POST',
      db: '_session',
      form: {
        name: username,
        password
      }
    }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/server/authn.html#post--_session
  function session (callback) {
    return relax({ db: '_session' }, callback)
  }

  // https://docs.couchdb.org/en/latest/api/server/common.html#api-server-root
  function info (callback) {
    return relax({ path: '' }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/server/common.html#get--_db_updates
  function updates (qs0, callback0) {
    const { opts, callback } = getCallback(qs0, callback0)
    return relax({
      db: '_db_updates',
      qs: opts
    }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/database/common.html#put--db
  function createDb (dbName, qs0, callback0) {
    const { opts, callback } = getCallback(qs0, callback0)
    if (missing(dbName)) {
      return callbackOrRejectError(callback)
    }
    return relax({ db: dbName, method: 'PUT', qs: opts }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/database/common.html#delete--db
  function destroyDb (dbName, callback) {
    if (missing(dbName)) {
      return callbackOrRejectError(callback)
    }
    return relax({ db: dbName, method: 'DELETE' }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/database/common.html#get--db
  function getDb (dbName, callback) {
    if (missing(dbName)) {
      return callbackOrRejectError(callback)
    }
    return relax({ db: dbName }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/server/common.html#get--_all_dbs
  function listDbs (callback) {
    return relax({ db: '_all_dbs' }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/server/common.html#get--_all_dbs
  function listDbsAsStream () {
    return relax({ db: '_all_dbs', stream: true })
  }

  // http://docs.couchdb.org/en/latest/api/database/compact.html#post--db-_compact
  function compactDb (dbName, ddoc, callback) {
    if (typeof ddoc === 'function') {
      callback = ddoc
      ddoc = null
    }
    if (missing(dbName)) {
      return callbackOrRejectError(callback)
    }
    return relax({
      db: dbName,
      doc: '_compact',
      att: ddoc,
      method: 'POST'
    }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/database/changes.html#get--db-_changes
  function changesDb (dbName, qs0, callback0) {
    const { opts, callback } = getCallback(qs0, callback0)
    if (missing(dbName)) {
      return callbackOrRejectError(callback)
    }
    return relax({ db: dbName, path: '_changes', qs: opts }, callback)
  }

  function changesDbAsStream (dbName, opts) {
    return relax({ db: dbName, path: '_changes', stream: true, qs: opts })
  }

  function _serializeAsUrl (db) {
    if (typeof db === 'object' && db.config && db.config.url && db.config.db) {
      return urlResolveFix(db.config.url, encodeURIComponent(db.config.db))
    } else {
      try {
        // if it parses, return it
        const parsed = new URL(db)
        return parsed.toString()
      } catch (e) {
        // otherwise treat it as a database name
        return urlResolveFix(cfg.url, encodeURIComponent(db))
      }
    }
  }

  // http://docs.couchdb.org/en/latest/api/server/common.html#post--_replicate
  function replicateDb (source, target, opts0, callback0) {
    const { opts, callback } = getCallback(opts0, callback0)

    if (missing(source, target)) {
      return callbackOrRejectError(callback)
    }

    // _replicate
    opts.source = _serializeAsUrl(source)
    opts.target = _serializeAsUrl(target)

    return relax({ db: '_replicate', body: opts, method: 'POST' }, callback)
  }

  // http://docs.couchdb.org/en/latest/api/server/common.html#uuids
  function uuids (count, callback) {
    if (typeof count === 'function') {
      callback = count
      count = 1
    }
    count = count || 1
    return relax({ method: 'GET', path: '_uuids', qs: { count } }, callback)
  }

  // http://guide.couchdb.org/draft/replication.html
  function enableReplication (source, target, opts0, callback0) {
    const { opts, callback } = getCallback(opts0, callback0)

    if (missing(source, target)) {
      return callbackOrRejectError(callback)
    }

    // _replicator
    opts.source = _serializeAsUrl(source)
    opts.target = _serializeAsUrl(target)

    return relax({ db: '_replicator', body: opts, method: 'POST' }, callback)
  }

  // http://guide.couchdb.org/draft/replication.html
  function queryReplication (id, opts0, callback0) {
    const { opts, callback } = getCallback(opts0, callback0)
    if (missing(id)) {
      return callbackOrRejectError(callback)
    }
    return relax({ db: '_replicator', method: 'GET', path: id, qs: opts }, callback)
  }

  // http://guide.couchdb.org/draft/replication.html
  function disableReplication (id, rev, opts0, callback0) {
    const { opts, callback } = getCallback(opts0, callback0)
    if (missing(id, rev)) {
      return callbackOrRejectError(callback)
    }
    const req = {
      db: '_replicator',
      method: 'DELETE',
      path: id,
      qs: Object.assign(opts, { rev })
    }
    return relax(req, callback)
  }

  function docModule (dbName) {
    let docScope = {}
    dbName = decodeURIComponent(dbName)

    // http://docs.couchdb.org/en/latest/api/document/common.html#put--db-docid
    // http://docs.couchdb.org/en/latest/api/database/common.html#post--db
    function insertDoc (doc, qs0, callback0) {
      const req = { db: dbName, body: doc, method: 'POST' }

      let { opts, callback } = getCallback(qs0, callback0)

      if (typeof opts === 'string') {
        opts = { docName: opts }
      }

      if (opts) {
        if (opts.docName) {
          req.doc = opts.docName
          req.method = 'PUT'
          delete opts.docName
        }
        req.qs = opts
      }

      return relax(req, callback)
    }

    // http://docs.couchdb.org/en/latest/api/document/common.html#delete--db-docid
    function destroyDoc (docName, rev, callback) {
      if (missing(docName)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        doc: docName,
        method: 'DELETE',
        qs: { rev }
      }, callback)
    }

    // http://docs.couchdb.org/en/latest/api/document/common.html#get--db-docid
    function getDoc (docName, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)

      if (missing(docName)) {
        return callbackOrRejectError(callback)
      }

      return relax({ db: dbName, doc: docName, qs: opts }, callback)
    }

    // http://docs.couchdb.org/en/latest/api/document/common.html#head--db-docid
    function headDoc (docName, callback) {
      if (missing(docName)) {
        return callbackOrRejectError(callback)
      }
      if (callback) {
        relax({
          db: dbName,
          doc: docName,
          method: 'HEAD',
          qs: {}
        }, callback)
      } else {
        // this function doesn't pass on the Promise from relax because it needs
        // to return the headers when resolving the Promise
        return new Promise(function (resolve, reject) {
          relax({
            db: dbName,
            doc: docName,
            method: 'HEAD',
            qs: {}
          }, function (err, body, headers) {
            if (err) {
              reject(err)
            } else {
              resolve(headers)
            }
          })
        })
      }
    }

    // http://docs.couchdb.org/en/latest/api/database/bulk-api.html#get--db-_all_docs
    function listDoc (qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      return relax({ db: dbName, path: '_all_docs', qs: opts }, callback)
    }

    // http://docs.couchdb.org/en/latest/api/database/bulk-api.html#get--db-_all_docs
    function listDocAsStream (opts) {
      return relax({ db: dbName, path: '_all_docs', qs: opts, stream: true })
    }

    // http://docs.couchdb.org/en/latest/api/database/bulk-api.html#post--db-_all_docs
    function fetchDocs (docNames, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      opts.include_docs = true

      if (missing(docNames) || typeof docNames !== 'object' ||
          !docNames.keys || !Array.isArray(docNames.keys) ||
          docNames.keys.length === 0) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_all_docs',
        method: 'POST',
        qs: opts,
        body: docNames
      }, callback)
    }

    function fetchRevs (docNames, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)

      if (missing(docNames) || typeof docNames !== 'object' ||
          !docNames.keys || !Array.isArray(docNames.keys) ||
          docNames.keys.length === 0) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_all_docs',
        method: 'POST',
        qs: opts,
        body: docNames
      }, callback)
    }

    function view (ddoc, viewName, meta, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)

      if (missing(ddoc, viewName) && !meta.viewPath) {
        return callbackOrRejectError(callback)
      }

      if (typeof meta.stream !== 'boolean') {
        meta.stream = false
      }

      // prevent mutation of the client qs object by using a clone
      const qs1 = Object.assign({}, opts)

      const viewPath = meta.viewPath || '_design/' + ddoc + '/_' + meta.type +
            '/' + viewName

      if (meta.type === 'search') {
        return relax({
          db: dbName,
          path: viewPath,
          method: 'POST',
          body: qs1,
          stream: meta.stream
        }, callback)
      } else if (qs1 && qs1.keys) {
        const body = { keys: qs1.keys }
        delete qs1.keys
        return relax({
          db: dbName,
          path: viewPath,
          method: 'POST',
          qs: qs1,
          body,
          stream: meta.stream
        }, callback)
      } else if (qs1 && qs1.queries) {
        const body = { queries: qs1.queries }
        delete qs1.queries
        return relax({
          db: dbName,
          path: viewPath,
          method: 'POST',
          qs: qs1,
          body
        }, callback)
      } else {
        const req = {
          db: dbName,
          method: meta.method || 'GET',
          path: viewPath,
          qs: qs1,
          stream: meta.stream
        }

        if (meta.body) {
          req.body = meta.body
        }

        return relax(req, callback)
      }
    }

    // http://docs.couchdb.org/en/latest/api/ddoc/views.html#post--db-_design-ddoc-_view-view
    function viewDocs (ddoc, viewName, qs, callback) {
      return view(ddoc, viewName, { type: 'view' }, qs, callback)
    }

    // http://docs.couchdb.org/en/latest/api/ddoc/views.html#post--db-_design-ddoc-_view-view
    function viewDocsAsStream (ddoc, viewName, qs) {
      return view(ddoc, viewName, { type: 'view', stream: true }, qs)
    }

    // cloudant
    function viewSearch (ddoc, viewName, qs, callback) {
      return view(ddoc, viewName, { type: 'search' }, qs, callback)
    }

    // cloudant
    function viewSearchAsStream (ddoc, viewName, qs) {
      return view(ddoc, viewName, { type: 'search', stream: true }, qs)
    }

    // http://docs.couchdb.org/en/latest/api/ddoc/render.html#get--db-_design-ddoc-_show-func
    function showDoc (ddoc, viewName, docName, qs, callback) {
      if (missing(ddoc, viewName, docName)) {
        return callbackOrRejectError(callback)
      }

      return view(ddoc, viewName + '/' + docName, { type: 'show' }, qs, callback)
    }

    // http://docs.couchdb.org/en/latest/api/ddoc/render.html#put--db-_design-ddoc-_update-func-docid
    function updateWithHandler (ddoc, viewName, docName, body, callback) {
      if (typeof body === 'function') {
        callback = body
        body = undefined
      }
      if (missing(ddoc, viewName, docName)) {
        return callbackOrRejectError(callback)
      }
      return view(ddoc, viewName + '/' + encodeURIComponent(docName), {
        type: 'update',
        method: 'PUT',
        body
      }, callback)
    }

    function viewWithList (ddoc, viewName, listName, qs, callback) {
      return view(ddoc, listName + '/' + viewName, {
        type: 'list'
      }, qs, callback)
    }

    function viewWithListAsStream (ddoc, viewName, listName, qs, callback) {
      return view(ddoc, listName + '/' + viewName, {
        type: 'list', stream: true
      }, qs, callback)
    }

    // http://docs.couchdb.org/en/latest/api/database/bulk-api.html#post--db-_bulksDoc
    function bulksDoc (docs, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      return relax({
        db: dbName,
        path: '_bulk_docs',
        body: docs,
        method: 'POST',
        qs: opts
      }, callback)
    }

    // http://docs.couchdb.org/en/latest/api/document/common.html#creating-multiple-attachments
    function insertMultipart (doc, attachments, qs, callback) {
      if (typeof qs === 'string') {
        qs = { docName: qs }
      }
      qs = qs || {}

      const docName = qs.docName
      delete qs.docName

      if (missing(doc, attachments, docName)) {
        return callbackOrRejectError(callback)
      }

      doc = Object.assign({ _attachments: {} }, doc)

      const multipart = []

      attachments.forEach(function (att) {
        doc._attachments[att.name] = {
          follows: true,
          length: Buffer.isBuffer(att.data) ? att.data.length : Buffer.byteLength(att.data),
          /* jscs:disable requireCamelCaseOrUpperCaseIdentifiers */
          content_type: att.content_type
        }
        multipart.push(att)
      })

      multipart.unshift({
        content_type: 'application/json',
        data: JSON.stringify(doc),
        name: 'document'
      })

      return relax({
        db: dbName,
        method: 'PUT',
        contentType: 'multipart/related',
        doc: docName,
        qs,
        multipart
      }, callback)
    }

    function getMultipart (docName, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      opts.attachments = true

      if (missing(docName)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        doc: docName,
        encoding: null,
        accept: 'multipart/related',
        qs: opts
      }, callback)
    }

    function insertAtt (docName, attName, att, contentType, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      if (missing(docName, attName, att, contentType)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        att: attName,
        method: 'PUT',
        contentType,
        doc: docName,
        qs: opts,
        body: att,
        dontStringify: true
      }, callback)
    }

    function getAtt (docName, attName, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)

      if (missing(docName, attName)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        att: attName,
        doc: docName,
        qs: opts,
        encoding: null,
        dontParse: true
      }, callback)
    }

    function getAttAsStream (docName, attName, opts) {
      return relax({
        db: dbName,
        att: attName,
        doc: docName,
        qs: opts,
        stream: true,
        encoding: null,
        dontParse: true
      })
    }

    function destroyAtt (docName, attName, qs, callback) {
      if (missing(docName, attName)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        att: attName,
        method: 'DELETE',
        doc: docName,
        qs
      }, callback)
    }

    function find (query, callback) {
      if (missing(query) || typeof query !== 'object') {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_find',
        method: 'POST',
        body: query
      }, callback)
    }

    function findAsStream (query) {
      return relax({
        db: dbName,
        path: '_find',
        method: 'POST',
        body: query,
        stream: true
      })
    }

    function createIndex (indexDef, callback) {
      if (missing(indexDef) || typeof indexDef !== 'object') {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_index',
        method: 'POST',
        body: indexDef
      }, callback)
    }

    function partitionInfo (partitionKey, callback) {
      if (missing(partitionKey)) {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partitionKey)
      }, callback)
    }

    function partitionedList (partitionKey, qs0, callback0) {
      const { opts, callback } = getCallback(qs0, callback0)
      if (missing(partitionKey)) {
        return callbackOrRejectError(callback)
      }
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partitionKey) + '/_all_docs',
        qs: opts
      }, callback)
    }

    function partitionedListAsStream (partitionKey, qs) {
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partitionKey) + '/_all_docs',
        qs,
        stream: true
      })
    }

    function partitionedFind (partition, query, callback) {
      if (missing(partition, query) || typeof query !== 'object') {
        return callbackOrRejectError(callback)
      }

      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_find',
        method: 'POST',
        body: query
      }, callback)
    }

    function partitionedFindAsStream (partition, query) {
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_find',
        method: 'POST',
        body: query,
        stream: true
      })
    }

    function partitionedSearch (partition, ddoc, searchName, opts, callback) {
      if (missing(partition, ddoc, searchName, opts) || typeof opts !== 'object') {
        return callbackOrRejectError(callback)
      }
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_design/' + ddoc + '/_search/' + searchName,
        qs: opts
      }, callback)
    }

    function partitionedSearchAsStream (partition, ddoc, searchName, opts) {
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_design/' + ddoc + '/_search/' + searchName,
        qs: opts,
        stream: true
      })
    }

    function partitionedView (partition, ddoc, viewName, opts, callback) {
      if (missing(partition, ddoc, viewName)) {
        return callbackOrRejectError(callback)
      }
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_design/' + ddoc + '/_view/' + viewName,
        qs: opts
      }, callback)
    }

    function partitionedViewAsStream (partition, ddoc, viewName, opts) {
      return relax({
        db: dbName,
        path: '_partition/' + encodeURIComponent(partition) + '/_design/' + ddoc + '/_view/' + viewName,
        qs: opts,
        stream: true
      })
    }

    // db level exports
    docScope = {
      info: function (cb) {
        return getDb(dbName, cb)
      },
      replicate: function (target, opts, cb) {
        return replicateDb(dbName, target, opts, cb)
      },
      compact: function (cb) {
        return compactDb(dbName, cb)
      },
      changes: function (qs, cb) {
        return changesDb(dbName, qs, cb)
      },
      changesAsStream: function (qs) {
        return changesDbAsStream(dbName, qs)
      },
      changesReader: new ChangesReader(dbName, relax),
      auth,
      session,
      insert: insertDoc,
      get: getDoc,
      head: headDoc,
      destroy: destroyDoc,
      bulk: bulksDoc,
      list: listDoc,
      listAsStream: listDocAsStream,
      fetch: fetchDocs,
      fetchRevs,
      config: { url: cfg.url, db: dbName },
      multipart: {
        insert: insertMultipart,
        get: getMultipart
      },
      attachment: {
        insert: insertAtt,
        get: getAtt,
        getAsStream: getAttAsStream,
        destroy: destroyAtt
      },
      show: showDoc,
      atomic: updateWithHandler,
      updateWithHandler,
      baseView: view,
      search: viewSearch,
      searchAsStream: viewSearchAsStream,
      view: viewDocs,
      viewAsStream: viewDocsAsStream,
      find,
      findAsStream,
      createIndex,
      viewWithList,
      viewWithListAsStream,
      server: serverScope,
      replication: {
        enable: function (target, opts, cb) {
          return enableReplication(dbName, target, opts, cb)
        },
        disable: function (id, revision, opts, cb) {
          return disableReplication(id, revision, opts, cb)
        },
        query: function (id, opts, cb) {
          return queryReplication(id, opts, cb)
        }
      },
      partitionInfo,
      partitionedList,
      partitionedListAsStream,
      partitionedFind,
      partitionedFindAsStream,
      partitionedSearch,
      partitionedSearchAsStream,
      partitionedView,
      partitionedViewAsStream
    }

    docScope.view.compact = function (ddoc, cb) {
      return compactDb(dbName, ddoc, cb)
    }

    return docScope
  }

  // server level exports
  serverScope = Object.assign(serverScope, {
    db: {
      create: createDb,
      get: getDb,
      destroy: destroyDb,
      list: listDbs,
      listAsStream: listDbsAsStream,
      use: docModule,
      scope: docModule,
      compact: compactDb,
      replicate: replicateDb,
      replication: {
        enable: enableReplication,
        disable: disableReplication,
        query: queryReplication
      },
      changes: changesDb,
      updates
    },
    use: docModule,
    scope: docModule,
    request: relax,
    relax,
    dinosaur: relax,
    auth,
    session,
    updates,
    uuids,
    info
  })

  const db = maybeExtractDatabaseComponent()

  return db ? docModule(db) : serverScope
}

/*
 * and now an ascii dinosaur
 *              _
 *            / _) ROAR! i'm a vegan!
 *     .-^^^-/ /
 *  __/       /
 * /__.|_|-|_|
 *
 * thanks for visiting! come again!
 */

function urlResolveFix (couchUrl, dbName) {
  if (/[^/]$/.test(couchUrl)) {
    couchUrl += '/'
  }
  return new URL(dbName, couchUrl).toString()
}
