Uploading files remotely on Selenium WebDriver using PHP

后端 未结 1 717
囚心锁ツ
囚心锁ツ 2021-02-09 06:52

I\'ve been searching around StackOverflow (and other resources) on how to remotely upload files on Selenium WebDriver with PHP. I\'ve read this http://saucelabs.com/blog/index.p

1条回答
  •  醉话见心
    2021-02-09 07:46

    I was able to determine that the JsonWireProtocol to upload a file would be /session//file by checking out the raw log on the SauceLabs.com blog post (https://saucelabs.com/jobs/1a408cf60af0601f49052f66fa37812c/selenium-server.log) so with that, I created this function to add-in to the php-webdriver-bindings library:

    /**
     * Send a file to your Remote WebDriver server
     * This will return the local URL of the file you uploaded, which will then
     * let you use sendKeys in file input elements
     * @params String $value - a local or remote file to send
     * @return String $resopnseValue - the local directory where the file resides on the remote server
     */
    public function sendFile($value) {
        $file = @file_get_contents($value);
    
        if( $file === false ) {
            return false;
        }
    
        $file = base64_encode($file);
        $request = $this->requestURL . "/file";
        $session = $this->curlInit($request);
        $args = array( 'file' => $file );
        $postargs = json_encode($args);
        $this->preparePOST($session, $postargs);
        $response = trim(curl_exec($session));
    
        $responseValue = $this->extractValueFromJsonResponse($response);
        return $responseValue;
    }
    

    Add this to the WebDriver.php file.

    To use, just do something like this:

    ...
    $file_location = $webdriver->sendFile('http://test.com/some/file.zip');
    $file_input = $webdriver->findElementBy(LocatorStrategy::id, 'uploadfile');
    $file_input->sendKeys(array($file_location));
    

    I hope this will help other developers, spent like 3 hours looking for the answer to this.

    Update:

    I had to change this due to getting this error:

    Expected there to be only 1 file. There were: 0
    

    Hopefully putting this here would get Google results (I tried searching for the error message on Google and the only results it could find were the references to the source code on Google Code).

    To solve this problem, I was able to deduce that the file you send actually needs to be zipped. So I've augmented the source code to use PHP's ZipArchive library. I will keep the old code on top for record-keeping, but please use the new code here:

    public function sendFile($value, $file_extension = '')
    {   
        $zip = new ZipArchive();
    
        $filename_hash = sha1(time().$value);
    
        $zip_filename = "{$filename_hash}_zip.zip";
        if( $zip->open($zip_filename, ZIPARCHIVE::CREATE) === false ) {
            echo 'WebDriver sendFile $zip->open failed\n';
            return false;
        }
    
        $file_data = @file_get_contents($value);
        if( $file_data === false ) {
            throw new Exception('WebDriver sendFile file_get_contents failed');
        }
    
        $filename = "{$filename_hash}.{$file_extension}";
        if( @file_put_contents($filename, $file_data) === false ) {
            throw new Exception('WebDriver sendFile file_put_contents failed');
        }
    
        $zip->addFile($filename, "{$filename_hash}.{$file_extension}");
        $zip->close();
    
        $zip_file = @file_get_contents($zip_filename);
        if( $zip_file === false ) {
            throw new Exception('WebDriver sendFile file_get_contents for $zip_file failed');
        }
    
        $file = base64_encode($zip_file);
    
        $request = $this->requestURL . "/file";
        $session = $this->curlInit($request);
        $args = array( 'file' => $file );
        $postargs = json_encode($args);
        $this->preparePOST($session, $postargs);
        $response = trim(curl_exec($session));
    
        return $this->extractValueFromJsonResponse($response);
    }
    

    Update: Turns out, you need to set two parameters on the $zip->addFile() method. Edited the above code to reflect the changes.

    0 讨论(0)
提交回复
热议问题