# frozen_string_literal: true
require 'spec_helper'
RSpec.describe TaskListToggleService, feature_category: :team_planning do
let(:markdown) do
<<-EOT.strip_heredoc
* [ ] Task 1
* [x] Task 2
A paragraph
1. [X] Item 1
- [ ] Sub-item 1
- [ ] loose list
with an embedded paragraph
+ [ ] No-break space (U+00A0)
2) [ ] Another item
EOT
end
let(:markdown_html) do
<<-EOT.strip_heredoc
A paragraph
-
Item 1
-
Another item
EOT
end
it 'checks Task 1' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: true,
line_source: '* [ ] Task 1',
line_number: 1
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[0]).to eq "* [x] Task 1\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
it 'unchecks Item 1' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: false,
line_source: '1. [X] Item 1',
line_number: 6
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[5]).to eq "1. [ ] Item 1\n"
expect(toggler.updated_markdown_html).to include('disabled> Item 1')
end
it 'checks task in loose list' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: true,
line_source: '- [ ] loose list',
line_number: 9
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[8]).to eq "- [x] loose list\n"
expect(toggler.updated_markdown_html).to include('disabled checked> loose list')
end
it 'checks task with no-break space' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: true,
line_source: '+ [ ] No-break space (U+00A0)',
line_number: 13
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[12]).to eq "+ [x] No-break space (U+00A0)\n"
expect(toggler.updated_markdown_html).to include('disabled checked> No-break space (U+00A0)')
end
it 'checks Another item' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: true,
line_source: '2) [ ] Another item',
line_number: 15
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[14]).to eq "2) [x] Another item"
expect(toggler.updated_markdown_html).to include('disabled checked> Another item')
end
it 'returns false if line_source does not match the text' do
toggler = described_class.new(
markdown, markdown_html,
toggle_as_checked: false,
line_source: '* [x] Task Added',
line_number: 2
)
expect(toggler.execute).to be_falsey
end
it 'tolerates \r\n line endings' do
rn_markdown = markdown.gsub("\n", "\r\n")
toggler = described_class.new(
rn_markdown,
markdown_html,
toggle_as_checked: true,
line_source: '* [ ] Task 1',
line_number: 1
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[0]).to eq "* [x] Task 1\r\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
it 'returns false if markdown is nil' do
toggler = described_class.new(
nil,
markdown_html,
toggle_as_checked: false,
line_source: '* [x] Task Added',
line_number: 2
)
expect(toggler.execute).to be_falsey
end
it 'returns false if markdown_html is nil' do
toggler = described_class.new(
markdown,
nil,
toggle_as_checked: false,
line_source: '* [x] Task Added',
line_number: 2
)
expect(toggler.execute).to be_falsey
end
it 'properly handles tasks in a blockquote' do
markdown =
<<-EOT.strip_heredoc
> > * [ ] Task 1
> * [x] Task 2
EOT
markdown_html = parse_markdown(markdown)
toggler = described_class.new(
markdown,
markdown_html,
toggle_as_checked: true,
line_source: '> > * [ ] Task 1',
line_number: 1
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[0]).to eq "> > * [x] Task 1\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
it 'properly handles a GitLab blockquote' do
markdown =
<<-EOT.strip_heredoc
>>>
gitlab blockquote
>>>
* [ ] Task 1
* [x] Task 2
EOT
markdown_html = parse_markdown(markdown)
toggler = described_class.new(
markdown,
markdown_html,
toggle_as_checked: true,
line_source: '* [ ] Task 1',
line_number: 5
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[4]).to eq "* [x] Task 1\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
context 'when clicking an embedded subtask' do
it 'properly handles it inside an unordered list' do
markdown =
<<-EOT.strip_heredoc
- - [ ] Task 1
- [x] Task 2
EOT
markdown_html = parse_markdown(markdown)
toggler = described_class.new(
markdown,
markdown_html,
toggle_as_checked: true,
line_source: '- - [ ] Task 1',
line_number: 1
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[0]).to eq "- - [x] Task 1\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
it 'properly handles it inside an ordered list' do
markdown =
<<-EOT.strip_heredoc
1. - [ ] Task 1
- [x] Task 2
EOT
markdown_html = parse_markdown(markdown)
toggler = described_class.new(
markdown,
markdown_html,
toggle_as_checked: true,
line_source: '1. - [ ] Task 1',
line_number: 1
)
expect(toggler.execute).to be_truthy
expect(toggler.updated_markdown.lines[0]).to eq "1. - [x] Task 1\n"
expect(toggler.updated_markdown_html).to include('disabled checked> Task 1')
end
end
def parse_markdown(markdown)
Banzai::Pipeline::FullPipeline.call(markdown, project: nil)[:output].to_html
end
end