jenkins-bot has submitted this change and it was merged. ( 
https://gerrit.wikimedia.org/r/393776 )

Change subject: Port full_text_browser.feature to nodejs
......................................................................


Port full_text_browser.feature to nodejs

Not a perfect port:
- Switched starting point to SRP instead of a random page (to avoid
  having go interfere with the expectations)
- Added Waffle* pages to hook tags, I see no reason why it was added
  like that
- Simplified the steps and did not implement the "imageresult" steps
- Added a optional suffix " and has an image link" to assert that the
  result is decorated with an image (meant to cover the imageresult
  check).

Change-Id: I5a57e1f68a7a2507466e8cea84b043f7372080cd
---
A tests/integration/features/full_text_browser.feature
M tests/integration/features/step_definitions/search_steps.js
M tests/integration/features/support/hooks.js
M tests/integration/features/support/pages/article_page.js
M tests/integration/features/support/pages/page.js
M tests/integration/features/support/pages/search_results_page.js
6 files changed, 245 insertions(+), 19 deletions(-)

Approvals:
  Cindy-the-browser-test-bot: Looks good to me, but someone else must approve
  EBernhardson: Looks good to me, approved
  jenkins-bot: Verified



diff --git a/tests/integration/features/full_text_browser.feature 
b/tests/integration/features/full_text_browser.feature
new file mode 100644
index 0000000..a2a1d49
--- /dev/null
+++ b/tests/integration/features/full_text_browser.feature
@@ -0,0 +1,102 @@
+@clean @phantomjs
+Feature: Full text search
+  Background:
+    Given I am at the search results page
+
+  @setup_main @setup_namespaces
+  Scenario Outline: Query string search
+    When I search for <term>
+    Then I am on a page titled Search results
+      And <first_result> is the first search result
+      But Two Words is <two_words_is_in> the search results
+  Examples:
+    | term                                 | first_result             | 
two_words_is_in |
+    | catapult                             | Catapult                 | in     
         |
+    | pickles                              | Two Words                | in     
         |
+    | rdir                                 | Two Words                | in     
         |
+    | talk:catapult                        | Talk:Two Words           | not in 
         |
+    | talk:intitle:words                   | Talk:Two Words           | not in 
         |
+    | template:pickles                     | Template:Template Test   | not in 
         |
+    | pickles/                             | Two Words                | in     
         |
+    | catapult/pickles                     | Two Words                | in     
         |
+    | File:"Screenshot, for test purposes" | File:Savepage-greyed.png | not in 
         |
+    # You can't search for text inside a <video> or <audio> tag
+    | "JavaScript disabled"                | none                     | not in 
         |
+    # You can't search for text inside the table of contants
+    | "3.1 Conquest of Persian empire"     | none                     | not in 
         |
+    # You can't search for the [edit] tokens that users can click to edit 
sections
+    | "Succession of Umar edit"            | none                     | not in 
         |
+
+  @setup_main
+  Scenario Outline: Searching for empty-string like values
+    When I search for <term>
+    Then I am on a page titled <title>
+      And there are no search results
+      And there are no errors reported
+  Examples:
+    | term                    | title          |
+    | the empty string        | Search         |
+    | ♙                       | Search results |
+    | %{exact: }              | Search results |
+    | %{exact:      }         | Search results |
+    | %{exact:              } | Search results |
+
+  @javascript_injection
+  Scenario: Searching for a page with javascript doesn't execute it (in this 
case, removing the page title)
+    When I search for Javascript findme
+    Then the title still exists
+
+  @file_text
+  Scenario: When you search for text that is in a file, you can find it!
+    When I search for File:debian rhino
+    Then File:Linux Distribution Timeline text version.pdf is the first search 
result and has an image link
+
+  @js_and_css
+  Scenario: JS pages don't corrupt the output
+    When I search for User:Tools/some.js jQuery
+    Then there is not alttitle on the first search result
+
+  @js_and_css
+  Scenario: CSS pages don't corrupt the output
+    When I search for User:Tools/some.css jQuery
+    Then there is not alttitle on the first search result
+
+  @setup_main
+  Scenario: Word count is output in the results
+    When I search for Two Words
+    Then there are search results with (4 words) in the data
+
+  @setup_main @filenames
+  Scenario Outline: Portions of file names
+    When I search for <term>
+    Then I am on a page titled Search results
+      And <first_result> is the first search result
+  Examples:
+    |            term            |          first_result          |
+    | File:Savepage-greyed.png   | File:Savepage-greyed.png       |
+    | File:Savepage              | File:Savepage-greyed.png       |
+    | File:greyed.png            | File:Savepage-greyed.png       |
+    | File:greyed                | File:Savepage-greyed.png       |
+    | File:Savepage png          | File:Savepage-greyed.png       |
+    | File:No_SVG.svg            | File:No SVG.svg                |
+    | File:No SVG.svg            | File:No SVG.svg                |
+    | File:No svg                | File:No SVG.svg                |
+    | File:svg.svg               | File:Somethingelse svg SVG.svg |
+
+  @setup_main
+  Scenario Outline: Text separated by a <br> tag is not jammed together
+    When I search for <term>
+    Then I am on a page titled Search results
+    Then <page> is the first search result
+    Examples:
+      |       term      |       page      |
+      |  Waffle Squash  |  Waffle Squash  |
+      | Waffle Squash 2 | Waffle Squash 2 |
+      |  wafflesquash   |       none      |
+
+  # Just take too long to run on a regular basis
+  # @huge
+  # Scenario: Searches for a huge phrase is reasonably fast (faster than the 
40 second timeout)
+  #   Given there are 3000 pages named Zeros%s with contents 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 
0 0 0 0 
+  #   When I search for 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 
0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 
0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0. 0.0.0.0.0.0.0.0.
+  #   Then Zeros is in the first search result
diff --git a/tests/integration/features/step_definitions/search_steps.js 
b/tests/integration/features/step_definitions/search_steps.js
index 3a3adc9..c56d012 100644
--- a/tests/integration/features/step_definitions/search_steps.js
+++ b/tests/integration/features/step_definitions/search_steps.js
@@ -1,13 +1,19 @@
 /*jshint esversion: 6,  node:true */
 
-const defineSupportCode = require('cucumber').defineSupportCode,
+const {defineSupportCode, defineParameterType} = require('cucumber'),
        SearchResultsPage = require('../support/pages/search_results_page'),
        ArticlePage = require('../support/pages/article_page'),
        TitlePage = require('../support/pages/title_page'),
        expect = require( 'chai' ).expect;
 
+defineParameterType( {
+       regexp: /.+/,
+       transformer: s => s === 'the empty string' ? '' : s.replace( 
/%{exact:([^}]*)}/g, '$1' ),
+       name: 'exact'
+} );
+
 defineSupportCode( function( {Then,When,Given} ) {
-       When( /^I go search for (.*)$/, function ( title ) {
+       When( /^I go search for (.+)$/, function ( title ) {
                return this.visit( SearchResultsPage.search( title ) );
        } );
 
@@ -15,7 +21,7 @@
                expect(SearchResultsPage.has_search_results(), 'there are no 
search results').to.equal(false);
        } );
 
-       When( /^I search for (.*)$/, function( search ) {
+       When( /^I search for (.+)$/, function( search ) {
                // If on the SRP already use the main search
                if ( SearchResultsPage.is_on_srp() ) {
                        SearchResultsPage.search_query = search;
@@ -33,10 +39,15 @@
 
        Then( /^there is no warning$/, function () {
                let msg = 'there is no warning';
-               expect(SearchResultsPage.get_warnings(), 
msg).to.have.lengthOf(0);
+               expect(SearchResultsPage.has_warnings(), msg).to.equal(false);
        } );
 
-       Then( /^(.*) is the first search result$/, function (result) {
+       Then( /^there are no errors reported$/, function () {
+               let msg = 'there are no errors reported';
+               expect(SearchResultsPage.has_errors(), msg).to.equal(false);
+       } );
+
+       Then( /^(.+) is the first search result( and has an image link)?$/, 
function (result, imagelink) {
                let msg = `${result} is the first search result`;
                if ( result === "none" ) {
                        expect(SearchResultsPage.has_search_results(), 
msg).to.equal(false);
@@ -44,22 +55,51 @@
                        expect(SearchResultsPage.is_on_srp(), 
msg).to.equal(true);
                        expect(SearchResultsPage.has_search_results(), 
msg).to.equal(true);
                        expect(SearchResultsPage.get_result_at(1), 
msg).to.equal(result);
+                       if ( imagelink ) {
+                               
expect(SearchResultsPage.get_result_image_link_at(1), msg).to.not.equal(null);
+                       }
                }
+       } );
+
+       Then( /^(.+) is( not)? in the search results$/, function (result, not) {
+               let msg = `${result} is${not === undefined ? '' : not} in the 
search results`;
+               expect(SearchResultsPage.is_on_srp(), msg).to.equal(true);
+               if ( not === undefined ) {
+                       expect(SearchResultsPage.has_search_results(), 
msg).to.equal(true);
+               }
+               expect(SearchResultsPage.in_search_results(result), 
msg).to.equal(not === undefined);
        } );
 
        Given( /^I am at the search results page$/, function() {
                this.visit( new TitlePage( 'Special:Search' ) );
        } );
 
-       When( /^I click the (.*) link$/, function( filter ) {
+       When( /^I click the (.+) link$/, function( filter ) {
                SearchResultsPage.click_filter( filter );
        } );
 
-       When( /^I click the (.*) labels?$/, function( filter ) {
+       When( /^I click the (.+) labels?$/, function( filter ) {
                let and_labels = filter.split(/, /, 10);
                for ( let labels of and_labels ) {
                        let or_labels = labels.split(/ or /, 10);
                        SearchResultsPage.select_namespaces( or_labels, true );
                }
        } );
+
+       Then( /^the title still exists$/, function() {
+               let msg = "the title still exists";
+               expect( ArticlePage.title_element().isExisting(), msg 
).to.equal(true);
+       } );
+
+       Then( /^there is not alttitle on the first search result$/, function() {
+               let msg = "there is not alttitle on the first search result";
+               expect(SearchResultsPage.get_search_alt_title_at(1, 
msg)).to.equal(null);
+       } );
+
+       Then( /^there are search results with \((.+)\) in the data$/, 
function(what) {
+               let msg = `there are search results with ${what} in the data`;
+               expect(SearchResultsPage.is_on_srp()).to.equal(true);
+               expect(SearchResultsPage.has_search_results(), 
msg).to.equal(true);
+               expect(SearchResultsPage.has_search_data_in_results(what), 
msg).to.equal(true);
+       } );
 });
diff --git a/tests/integration/features/support/hooks.js 
b/tests/integration/features/support/hooks.js
index 2c78666..19f560f 100644
--- a/tests/integration/features/support/hooks.js
+++ b/tests/integration/features/support/hooks.js
@@ -162,7 +162,9 @@
                        "\u0935\u093e\u0919\u094d\u200c\u092e\u092f": 
"\u0935\u093e\u0919\u094d\u200c\u092e\u092f",
                        "ChangeMe": "foo",
                        "Wikitext": "{{#tag:somebug}}",
-                       "Page with non ascii letters": "ἄνθρωπος, широкий"
+                       "Page with non ascii letters": "ἄνθρωπος, широкий",
+                       "Waffle Squash": articleText("wafflesquash.txt"),
+                       "Waffle Squash 2": "waffle<br>squash"
                }
        } ) );
 
diff --git a/tests/integration/features/support/pages/article_page.js 
b/tests/integration/features/support/pages/article_page.js
index f7c4450..1c8d63d 100644
--- a/tests/integration/features/support/pages/article_page.js
+++ b/tests/integration/features/support/pages/article_page.js
@@ -10,7 +10,11 @@
 class ArticlePage extends TitlePage {
 
        get articleTitle() {
-               return browser.getText("h1#firstHeading");
+               return this.title_element().getText();
+       }
+
+       title_element() {
+               return browser.element( "h1#firstHeading" );
        }
 
        /**
diff --git a/tests/integration/features/support/pages/page.js 
b/tests/integration/features/support/pages/page.js
index 81bb47c..bd9ce48 100644
--- a/tests/integration/features/support/pages/page.js
+++ b/tests/integration/features/support/pages/page.js
@@ -46,6 +46,15 @@
                } );
        }
 
+       collect_element_texts( selector ) {
+               let elements = browser.elements(selector).value;
+               let texts = [];
+               for ( let text of elements ) {
+                       texts.push( text.getText() );
+               }
+               return texts;
+       }
+
        get url() {
                return this._url;
        }
diff --git a/tests/integration/features/support/pages/search_results_page.js 
b/tests/integration/features/support/pages/search_results_page.js
index 3083c56..16473ae 100644
--- a/tests/integration/features/support/pages/search_results_page.js
+++ b/tests/integration/features/support/pages/search_results_page.js
@@ -15,16 +15,23 @@
        }
 
        has_search_results() {
-               return browser.elements(".searchresults 
p.mw-search-nonefound").value.length === 0;
+               return browser.elements(".searchresults 
ul.mw-search-results").value.length > 0;
        }
 
        get_warnings() {
-               let elements = browser.elements(".searchresults div.warningbox 
p").value;
-               let warnings = [];
-               for ( let warning of elements ) {
-                       warnings.push( warning.getText() );
-               }
-               return warnings;
+               return this.collect_element_texts(".searchresults 
div.warningbox p");
+       }
+
+       has_warnings() {
+               return this.get_warnings().length > 0;
+       }
+
+       get_errors() {
+               return this.collect_element_texts(".searchresults div.errorbox 
p");
+       }
+
+       has_errors() {
+               return this.get_errors().length > 0;
        }
 
        has_create_page_link() {
@@ -36,16 +43,78 @@
                        browser.elements("form#powersearch 
div#mw-search-top-table").value.length > 0;
        }
 
-       set search_query(search ) {
+       set search_query( search ) {
                browser.setValue( 'div#searchText input[name="search"]', search 
);
        }
 
        get search_query() {
-               browser.getValue( 'div#searchText input[name="search"]' );
+               return browser.getValue( 'div#searchText input[name="search"]' 
);
+       }
+
+       get_result_element_at( nth ) {
+               let resultLink = this.results_block().element( 
`a[data-serp-pos=\"${nth-1}\"]` );
+               if ( !resultLink.isExisting() ) {
+                       return null;
+               }
+               return resultLink.element("..");
+       }
+
+       get_result_image_link_at( nth ) {
+               let resElem = this.get_result_element_at( nth );
+               if ( resElem === null ) {
+                       return null;
+               }
+               // Image links are inside a table
+               // move to the tr parent to switch the td holding the images
+               // <tbody>
+               //  <tr>
+               //    <td>[THUMB IMAGE LINK BLOCK]</td>
+               //    <td>[RESULT ELEMENT BLOCK] position returned by 
get_result_element_at</td>
+               //  </tr>
+               // </tbody>
+               let tr = resElem.element("..");
+               if ( tr.getTagName() !== 'tr' ) {
+                       return null;
+               }
+               let imageTag = tr.element( 'td a.image img' );
+               if ( imageTag.isExisting() ) {
+                       return imageTag.getAttribute( 'src' );
+               }
+               return null;
+       }
+
+       has_search_data_in_results( data ) {
+               return this.results_block().element( 
`div.mw-search-result-data*=${data}`).isExisting();
+       }
+
+       get_search_alt_title_at( nth ) {
+               let resultBlock = this.get_result_element_at( nth );
+               if ( resultBlock === null ) {
+                       return null;
+               }
+               let elt = resultBlock.element("span.searchalttitle");
+               if ( elt.isExisting() ) {
+                       return elt.getText();
+               }
+               return null;
        }
 
        get_result_at( nth ) {
-               return browser.getAttribute( `ul.mw-search-results li 
div.mw-search-result-heading a[data-serp-pos=\"${nth-1}\"]`, 'title' );
+               return this.results_block().getAttribute( 
`a[data-serp-pos=\"${nth-1}\"]`, 'title' );
+       }
+
+       in_search_results( title ) {
+               let elt = this.results_block().element(`a[title="${title}"]` );
+               return elt.isExisting();
+       }
+
+       results_block() {
+               let elt = browser.elements( "div.searchresults" );
+
+               if ( !elt.value ) {
+                       throw new Error("Cannot locate search results block, 
are you on the SRP?");
+               }
+               return elt;
        }
 
        click_search() {

-- 
To view, visit https://gerrit.wikimedia.org/r/393776
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings

Gerrit-MessageType: merged
Gerrit-Change-Id: I5a57e1f68a7a2507466e8cea84b043f7372080cd
Gerrit-PatchSet: 3
Gerrit-Project: mediawiki/extensions/CirrusSearch
Gerrit-Branch: master
Gerrit-Owner: DCausse <[email protected]>
Gerrit-Reviewer: Cindy-the-browser-test-bot <[email protected]>
Gerrit-Reviewer: DCausse <[email protected]>
Gerrit-Reviewer: EBernhardson <[email protected]>
Gerrit-Reviewer: Gehel <[email protected]>
Gerrit-Reviewer: Smalyshev <[email protected]>
Gerrit-Reviewer: jenkins-bot <>

_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits

Reply via email to