otwarchive-symphonyarchive/features/step_definitions/work_search_steps.rb

515 lines
17 KiB
Ruby
Raw Normal View History

2026-03-11 22:22:11 +00:00
### GIVEN
Given /^a set of alternate universe works for searching$/ do
step %{basic tags}
# Create a metatag with a syn
step %{a canonical freeform "Alternate Universe"}
step %{a synonym "AU" of the tag "Alternate Universe"}
# Create a subtag with a syn
step %{a canonical freeform "Alternate Universe - High School"}
step %{a synonym "High School AU" of the tag "Alternate Universe - High School"}
# Create another subtag
step %{a canonical freeform "Alternate Universe - Coffee Shops & Cafés"}
# Set up the tree
step %{"Alternate Universe" is a metatag of the freeform "Alternate Universe - High School"}
step %{"Alternate Universe" is a metatag of the freeform "Alternate Universe - Coffee Shops & Cafés"}
# Create a work with every tag except Alternate Universe - High School, and a
# work with the unwrangled tag Coffee Shop AU
["Alternate Universe",
"AU",
"High School AU",
"Alternate Universe - Coffee Shops & Cafés",
"Coffee Shop AU"].each do |freeform|
FactoryBot.create(:work, freeform_string: freeform)
end
# Create a work with a summary that is a text match for both the unwrangled
# tag (Coffee Shop AU) and the metatag's syn (AU)
FactoryBot.create(:work, summary: "A humble Coffee Shop AU")
# Create a work with a character tag that is a text match for the metatag's
# syn (AU)
FactoryBot.create(:work, character_string: "AU Character")
step %{all indexing jobs have been run}
end
Given /^a set of Steve Rogers works for searching$/ do
step %{basic tags}
# Create two fandoms
step %{a canonical fandom "Marvel Cinematic Universe"}
step %{a canonical fandom "The Avengers (Marvel Movies)"}
# Create a character with a syn
step %{a canonical character "Steve Rogers"}
step %{a synonym "Captain America" of the tag "Steve Rogers"}
# Create a meta tag for that character
step %{a canonical character "Steve"}
step %{"Steve" is a metatag of the character "Steve Rogers"}
# Create a work for each character tag in each fandom
["Marvel Cinematic Universe", "The Avengers (Marvel Movies)"].each do |fandom|
["Steve Rogers", "Captain America"].each do |character|
FactoryBot.create(:work,
fandom_string: fandom,
character_string: character)
end
end
# Create a work without Steve as a character but with him in a relationship
FactoryBot.create(:work,
relationship_string: "Steve Rogers/Tony Stark")
# Create a work that only mentions Steve in the summary
FactoryBot.create(:work,
summary: "Bucky thinks about his pal Steve Rogers.")
step %{all indexing jobs have been run}
end
Given /^a set of Kirk\/Spock works for searching$/ do
step %{basic tags}
# Create a relationship with two syns
step %{a canonical relationship "James T. Kirk/Spock"}
step %{a synonym "K/S" of the tag "James T. Kirk/Spock"}
step %{a synonym "Spirk" of the tag "James T. Kirk/Spock"}
# Create a work for each tag
["James T. Kirk/Spock", "K/S", "Spirk"].each do |relationship|
FactoryBot.create(:work, relationship_string: relationship)
end
# Create a F/M work using one of the synonyms
FactoryBot.create(:work,
title: "The Genderswap K/S Work That Uses a Synonym",
relationship_string: "Spirk",
category_string: "F/M")
step %{all indexing jobs have been run}
end
Given /^a set of Spock\/Uhura works for searching$/ do
step %{basic tags}
# Create a canonical two-character relationship with a syn
step %{a canonical relationship "Spock/Nyota Uhura"}
step %{a synonym "Uhura/Spock" of the tag "Spock/Nyota Uhura"}
# Create a threesome with a name that is a partial match for the relationship
step %{a canonical relationship "James T. Kirk/Spock/Nyota Uhura"}
# Create a work for each tag
["Spock/Nyota Uhura",
"Uhura/Spock",
"James T. Kirk/Spock/Nyota Uhura"].each do |relationship|
FactoryBot.create(:work,
relationship_string: relationship)
end
step %{all indexing jobs have been run}
end
Given "a set of Ed Stede works for searching" do
step %{basic tags}
# Create a relationship with a syn
step %{a canonical relationship "Blackbeard | Edward Teach/Stede Bonnet"}
step %{a synonym "Ed/Stede" of the tag "Blackbeard | Edward Teach/Stede Bonnet"}
# Create a work for each tag or set of tags (all are otp: true)
["Ed/Stede",
"Blackbeard | Edward Teach/Stede Bonnet",
"Blackbeard | Edward Teach/Stede Bonnet, Ed/Stede"].each do |relationship|
FactoryBot.create(:work, relationship_string: relationship)
end
# Create a work with no relationship tag (an otp: false work)
FactoryBot.create(:work, title: "The Work Without a Relationship")
# Create a work with two unconnected relationship tags (an otp: false work)
FactoryBot.create(:work,
title: "The Work With Multiple Ships",
relationship_string: "Ed/Stede, Ed/Izzy")
step %{all indexing jobs have been run}
end
Given "a set of crossover works for searching" do
step %{basic tags}
# Create two unrelated fandoms, one with a syn
step %{a canonical fandom "Unrelated Fandom"}
step %{a canonical fandom "Hermitcraft SMP"}
step %{a synonym "Hermitcraft" of the tag "Hermitcraft SMP"}
# Create a fandom and make it the metatag of one of the fandoms
step %{a canonical fandom "Video Blogging RPF"}
step %{"Video Blogging RPF" is a metatag of the fandom "Hermitcraft SMP"}
# Create a work for each tag or set of tags (none are crossovers)
["Video Blogging RPF",
"Hermitcraft SMP",
"Hermitcraft SMP, Hermitcraft",
"Hermitcraft SMP, Video Blogging RPF",
"Hermitcraft, Video Blogging RPF"].each do |fandom|
FactoryBot.create(:work, fandom_string: fandom)
end
# Create three works with two unconnected fandom tags (crossover works)
FactoryBot.create(:work,
title: "First Work With Multiple Fandoms",
fandom_string: "Hermitcraft SMP, Unrelated Fandom")
FactoryBot.create(:work,
title: "Second Work With Multiple Fandoms",
fandom_string: "Hermitcraft, Unrelated Fandom")
FactoryBot.create(:work,
title: "Third Work With Multiple Fandoms",
fandom_string: "Video Blogging RPF, Unrelated Fandom")
step %{all indexing jobs have been run}
end
Given /^a set of works with various categories for searching$/ do
step %{basic tags}
# Create one work with each category
%w(Gen Other F/F Multi F/M M/M).each do |category|
FactoryBot.create(:work, category_string: category)
end
# Create one work using multiple categories
FactoryBot.create(:work, category_string: "M/M, F/F")
step %{all indexing jobs have been run}
end
Given /^a set of works with comments for searching$/ do
step %{basic tags}
counts = {
"Work 1" => 0,
"Work 2" => 1,
"Work 3" => 1,
"Work 4" => 1,
"Work 5" => 3,
"Work 6" => 3,
"Work 7" => 10
}
counts.each_pair do |title, comment_count|
work = FactoryBot.create(:work, title: title)
FactoryBot.create_list(:comment, comment_count, :by_guest,
commentable: work.last_posted_chapter)
end
step %{the statistics for all works are updated}
step %{all indexing jobs have been run}
end
Given /^a set of Star Trek works for searching$/ do
step %{basic tags}
# Create three related canonical fandoms
step %{a canonical fandom "Star Trek"}
step %{a canonical fandom "Star Trek: The Original Series"}
step %{a canonical fandom "Star Trek: The Original Series (Movies)"}
# Create a syn for one of the fandoms
step %{a synonym "ST: TOS" of the tag "Star Trek: The Original Series"}
# Create an unrelated fourth fandom we'll use for a crossover
step %{a canonical fandom "Battlestar Galactica (2003)"}
# Set up the tree for the related fandoms
step %{"Star Trek" is a metatag of the fandom "Star Trek: The Original Series"}
step %{"Star Trek: The Original Series" is a metatag of the fandom "Star Trek: The Original Series (Movies)"}
# Create a work using each of the related fandoms
["Star Trek", "Star Trek: The Original Series",
"Star Trek: The Original Series (Movies)", "ST: TOS"].each do |fandom|
FactoryBot.create(:work, fandom_string: fandom)
end
# Create a work with two fandoms (e.g. a crossover)
FactoryBot.create(:work,
fandom_string: "ST: TOS,
Battlestar Galactica (2003)")
# Create a work with an additional tag (freeform) that references the fandom
FactoryBot.create(:work,
fandom_string: "Battlestar Galactica (2003)",
freeform_string: "Star Trek Fusion")
step %{all indexing jobs have been run}
end
Given /^a set of works with bookmarks for searching$/ do
step %{basic tags}
counts = {
"Work 1" => 0,
"Work 2" => 1,
"Work 3" => 1,
"Work 4" => 2,
"Work 5" => 2,
"Work 6" => 4,
"Work 7" => 10
}
counts.each_pair do |title, bookmark_count|
work = FactoryBot.create(:work, title: title)
FactoryBot.create_list(:bookmark, bookmark_count, bookmarkable: work)
end
step %{the statistics for all works are updated}
step %{all indexing jobs have been run}
end
Given /^a set of works with various ratings for searching$/ do
step %{basic tags}
ratings = [ArchiveConfig.RATING_DEFAULT_TAG_NAME,
ArchiveConfig.RATING_GENERAL_TAG_NAME,
ArchiveConfig.RATING_TEEN_TAG_NAME,
ArchiveConfig.RATING_MATURE_TAG_NAME,
ArchiveConfig.RATING_EXPLICIT_TAG_NAME]
ratings.each do |rating|
FactoryBot.create(:work, rating_string: rating)
end
FactoryBot.create(:work,
rating_string: ArchiveConfig.RATING_DEFAULT_TAG_NAME,
summary: "Nothing explicit here.")
step %{all indexing jobs have been run}
end
Given /^a set of works with various warnings for searching$/ do
step %{basic tags}
step %{all warnings exist}
warnings = [ArchiveConfig.WARNING_DEFAULT_TAG_NAME,
ArchiveConfig.WARNING_NONE_TAG_NAME,
ArchiveConfig.WARNING_VIOLENCE_TAG_NAME,
ArchiveConfig.WARNING_DEATH_TAG_NAME,
ArchiveConfig.WARNING_NONCON_TAG_NAME,
ArchiveConfig.WARNING_CHAN_TAG_NAME]
# Create a work for each warning
warnings.each do |warning|
FactoryBot.create(:work, archive_warning_string: warning)
end
# Create a work that uses multiple warnings
FactoryBot.create(:work,
archive_warning_string: "#{ArchiveConfig.WARNING_DEFAULT_TAG_NAME},
#{ArchiveConfig.WARNING_NONE_TAG_NAME}")
step %{all indexing jobs have been run}
end
Given /^a set of works with various access levels for searching$/ do
# Create a draft
FactoryBot.create(:draft, title: "Draft Work")
# Create a work
FactoryBot.create(:work, title: "Posted Work")
# Create a work restricted to registered users
FactoryBot.create(:work, restricted: true, title: "Restricted Work")
# Create a work hidden by an admin
FactoryBot.create(:work,
hidden_by_admin: true,
title: "Work Hidden by Admin")
step %{all indexing jobs have been run}
end
Given "a set of old multilanguage works for searching" do
german = Language.find_or_create_by!(short: "de", name: "Deutsch")
FactoryBot.create(:work,
title: "My <strong>er German Work",
language: german,
authors: [ensure_user("testuser2").default_pseud])
FactoryBot.create(:work,
title: "unfinished",
complete: false,
expected_number_of_chapters: 2,
authors: [ensure_user("testuser").default_pseud])
step %{all indexing jobs have been run}
step %{it is currently 3 years from now}
end
Given "a set of works with stats for searching" do
many = FactoryBot.create(:work, title: "many")
FactoryBot.create_list(:kudo, 4, commentable: many)
many.stat_counter.update_attribute(:hit_count, 10_000)
less = FactoryBot.create(:work, title: "less")
FactoryBot.create(:kudo, commentable: less)
less.stat_counter.update_attribute(:hit_count, 500)
FactoryBot.create(:work, title: "none")
FactoryBot.create(:work, title: "unfinished", complete: false, expected_number_of_chapters: 2)
step %{the statistics for all works are updated}
step %{all indexing jobs have been run}
end
### WHEN
When /^I search for a simple term from the search box$/ do
step %{I am on the homepage}
step %{I fill in "site_search" with "first"}
step %{I press "Search"}
end
When /^I search for works containing "([^"]*)"$/ do |term|
step %{I am on the homepage}
step %{I fill in "site_search" with "#{term}"}
step %{I press "Search"}
end
When /^I search for works by "([^"]*)"$/ do |creator|
step %{I am on the homepage}
step %{I fill in "site_search" with "creator: #{creator}"}
step %{I press "Search"}
end
When /^I search for works without the "([^"]*)"(?: and "([^"]*)")? filter_ids?$/ do |tag1, tag2|
filter_id1 = Tag.find_by_name(tag1).filter_taggings.first.filter_id
filter_id2 = Tag.find_by_name(tag2).filter_taggings.first.filter_id if tag2
step %{I am on the homepage}
if tag2
fill_in("site_search", with: "-filter_ids: #{filter_id1} -filter_ids: #{filter_id2}")
else
fill_in("site_search", with: "-filter_ids: #{filter_id1}")
end
step %{I press "Search"}
end
When /^I exclude the tags? "([^"]*)"(?: and "([^"]*)")? by filter_id$/ do |tag1, tag2|
filter_id1 = Tag.find_by_name(tag1).filter_taggings.first.filter_id
filter_id2 = Tag.find_by_name(tag2).filter_taggings.first.filter_id if tag2
if tag2
fill_in('work_search_query', with: "-filter_ids: #{filter_id1} -filter_ids: #{filter_id2}")
else
fill_in('work_search_query', with: "-filter_ids: #{filter_id1}")
end
end
### THEN
Then /^the results should contain the ([^"]*) tag "([^"]*)"$/ do |type, tag|
selector = if type == "fandom"
"ol.work .fandoms"
elsif %w(rating category).include?(type)
"ol.work .required-tags .#{type}"
else
"ol.work .tags .#{type.pluralize}"
end
expect(page).to have_css(selector, text: tag)
end
Then /^the results should not contain the ([^"]*) tag "([^"]*)"$/ do |type, tag|
selector = if type == "fandom"
"ol.work .fandoms"
elsif %w(rating category).include?(type)
"ol.work .required-tags .#{type}"
else
"ol.work .tags .#{type.pluralize}"
end
expect(page).not_to have_css(selector, text: tag)
end
Then /^the results should contain (?:a|the) synonyms? of "([^"]*)"$/ do |tag|
tag = Tag.find_by_name(tag)
type = tag.type.downcase.pluralize
synonyms = tag.synonyms.map(&:name)
selector = if type == "fandoms"
"ol.work .fandoms"
else
"ol.work .tags .#{type}"
end
synonyms.each do |synonym|
expect(page).to have_css(selector, text: synonym)
end
end
Then /^the results should contain (?:a|the) subtags? of "([^"]*)"$/ do |tag|
tag = Tag.find_by_name(tag)
type = tag.type.downcase.pluralize
subtags = tag.sub_tags.map(&:name)
selector = if type == "fandoms"
"ol.work .fandoms"
else
"ol.work .tags .#{type}"
end
subtags.each do |subtag|
expect(page).to have_css(selector, text: subtag)
end
end
Then /^the results should contain a ([^"]*) mentioning "([^"]*)"$/ do |item, term|
selector = if item == "fandom"
"ol.work .fandoms"
elsif item == "summary"
"ol.work .summary"
else
"ol.work .tags .#{item.pluralize}"
end
expect(page).to have_css(selector, text: term)
end
Then /^the results should not contain a ([^"]*) mentioning "([^"]*)"$/ do |item, term|
selector = if item == "fandom"
"ol.work .fandoms"
elsif item == "summary"
"ol.work .summary"
else
"ol.work .tags .#{item.pluralize}"
end
expect(page).not_to have_css(selector, text: term)
end
Then /^the ([\d]+)(?:st|nd|rd|th) result should contain "([^"]*)"$/ do |n, text|
selector = "ol.work > li:nth-of-type(#{n})"
with_scope(selector) do
page.should have_content(text)
end
end
# If JavaScript is enabled and we want to check that information is retained
# when editing a search, we can't look at what is in the input -- we have to
# look at the contents of the ul that contains both the field and the added tags
Then /^"([^"]*)" should already be entered in the work search ([^"]*) autocomplete field$/ do |tag, field|
within(:xpath, "//input[@id=\"work_search_#{field.singularize}_names_autocomplete\"]/parent::li/parent::ul") do
page.should have_content(tag)
end
end
Then /^the search summary should include the filter_id for "([^"]*)"$/ do |tag|
filter_id = Tag.find_by_name(tag).filter_taggings.first.filter_id
step %{I should see "filter_ids: #{filter_id}" within "#main h4.heading"}
end
Then /^the results should contain only the restricted work$/ do
step %{I should see "Restricted Work"}
step %{I should not see "Posted Work"}
step %{I should not see "Work Hidden by Admin"}
step %{I should not see "Draft Work"}
end