// Licensed to the Software Freedom Conservancy (SFC) under one
// or more contributor license agreements.  See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership.  The SFC licenses this file
// to you 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.

'use strict'

const assert = require('assert')

const chrome = require('../chrome')
const edge = require('../edge')
const firefox = require('../firefox')
const ie = require('../ie')
const safari = require('../safari')
const test = require('../lib/test')
const { Browser } = require('../lib/capabilities')
const { Pages } = require('../lib/test')
const { Builder } = require('../../selenium-webdriver/index')

test.suite(function (env) {
  const BROWSER_MAP = new Map([
    [Browser.CHROME, chrome.Driver],
    [Browser.EDGE, edge.Driver],
    [Browser.FIREFOX, firefox.Driver],
    [Browser.INTERNET_EXPLORER, ie.Driver],
    [Browser.SAFARI, safari.Driver],
  ])

  if (BROWSER_MAP.has(env.browser.name)) {
    describe('builder creates thenable driver instances', function () {
      let driver

      after(() => driver && driver.quit())

      it(env.browser.name, function () {
        driver = env.builder().build()

        const want = BROWSER_MAP.get(env.browser.name)
        assert.ok(
          driver instanceof want,
          `want ${want.name}, but got ${driver.name}`
        )
        assert.strictEqual(typeof driver.then, 'function')

        return (
          driver
            .then((d) =>
              assert.ok(
                d instanceof want,
                `want ${want.name}, but got ${d.name}`
              )
            )
            // Load something so the safari driver doesn't crash from starting and
            // stopping in short time.
            .then(() => driver.get(Pages.echoPage))
        )
      })
    })
  }

  if (BROWSER_MAP.has(env.browser.name)) {
    describe('builder allows to set a single capability', function () {
      let driver

      after(() => driver && driver.quit())

      it(env.browser.name, async function () {
        let timeouts = { implicit: 0, pageLoad: 1000, script: 1000 }
        driver = new Builder()
          .setCapability('timeouts', timeouts)
          .forBrowser(env.browser.name)
          .build()

        let caps = await getCaps(driver);
        assert.deepEqual(caps.get('timeouts'), timeouts)
      })
    })
  }

  async function getCaps(driver) {
    return driver.getCapabilities();
  }
})

describe('Builder', function () {
  describe('catches incorrect use of browser options class', function () {
    function test(key, options) {
      it(key, async function () {
        let builder = new Builder().withCapabilities(
          new Capabilities()
            .set('browserName', 'fake-browser-should-not-try-to-start')
            .set(key, new options())
        )
        try {
          let driver = await builder.build()
          await driver.quit()
          return Promise.reject(Error('should have failed'))
        } catch (ex) {
          if (!(ex instanceof error.InvalidArgumentError)) {
            throw ex
          }
        }
      })
    }

    test('chromeOptions', chrome.Options)
    test('moz:firefoxOptions', firefox.Options)
    test('safari.options', safari.Options)
  })
})
@@ -909,24 +909,62 @@
 ('../edge')%0A
+const error = require('../lib/error')%0A
 const firefo
@@ -1196,16 +1196,30 @@
  Builder
+, Capabilities
  %7D = req
@@ -1230,36 +1230,8 @@
 ('..
-/../selenium-webdriver/index
 ')%0A%0A
@@ -3016,12 +3016,11 @@
   %7D%0A
-%7D)%0A%0A
+%0A  
 desc
@@ -3049,16 +3049,18 @@
 on () %7B%0A
+  
   descri
@@ -3130,16 +3130,18 @@
 ) %7B%0A    
+  
 function
@@ -3158,24 +3158,26 @@
  options) %7B%0A
+  
       it(key
@@ -3202,24 +3202,26 @@
 ) %7B%0A        
+  
 let builder 
@@ -3264,16 +3264,18 @@
         
+ 
+ 
 new Capa
@@ -3285,16 +3285,18 @@
 ities()%0A
+  
         
@@ -3367,24 +3367,26 @@
             
+  
 .set(key, ne
@@ -3398,16 +3398,18 @@
 ions())%0A
+  
         
@@ -3422,14 +3422,18 @@
     
+  
 try %7B%0A
+  
     
@@ -3483,16 +3483,18 @@
         
+  
 await dr
@@ -3511,24 +3511,26 @@
 )%0A          
+ 
+ 
 return Promi
@@ -3576,16 +3576,18 @@
         
+  
 %7D catch 
@@ -3603,16 +3603,18 @@
         
+ 
+ 
 if (!(ex
@@ -3652,24 +3652,26 @@
 ntError)) %7B%0A
+  
             
@@ -3685,26 +3685,30 @@
 x%0A          
-%7D%0A
+  %7D%0A  
         %7D%0A  
@@ -3715,18 +3715,24 @@
     
+  
 %7D)%0A    
+ 
+ 
 %7D%0A%0A
+  
     
@@ -3769,24 +3769,26 @@
 ptions)%0A    
+ 
+ 
 test('moz:fi
@@ -3815,24 +3815,26 @@
 ox.Options)%0A
+  
     test('sa
@@ -3864,15 +3864,22 @@
 ptions)%0A
+    %7D)%0A
   %7D)%0A%7D)

Fix builder test