# frozen_string_literal: true require 'spec_helper' describe Banzai::Filter::SyntaxHighlightFilter do include FilterSpecHelper shared_examples "XSS prevention" do |lang| it "escapes HTML tags" do # This is how a script tag inside a code block is presented to this filter # after Markdown rendering. result = filter(%{
<script>alert(1)</script>
}) expect(result.to_html).not_to include("") expect(result.to_html).to include("alert(1)") end end context "when no language is specified" do it "highlights as plaintext" do result = filter('
def fun end
') expect(result.to_html).to eq('
def fun end
') end include_examples "XSS prevention", "" end context "when a valid language is specified" do it "highlights as that language" do result = filter('
def fun end
') expect(result.to_html).to eq('
def fun end
') end include_examples "XSS prevention", "ruby" end context "when an invalid language is specified" do it "highlights as plaintext" do result = filter('
This is a test
') expect(result.to_html).to eq('
This is a test
') end include_examples "XSS prevention", "gnuplot" end context "languages that should be passed through" do let(:delimiter) { described_class::PARAMS_DELIMITER } let(:data_attr) { described_class::LANG_PARAMS_ATTR } %w(math mermaid plantuml suggestion).each do |lang| context "when #{lang} is specified" do it "highlights as plaintext but with the correct language attribute and class" do result = filter(%{
This is a test
}) expect(result.to_html).to eq(%{
This is a test
}) end include_examples "XSS prevention", lang end context "when #{lang} has extra params" do let(:lang_params) { 'foo-bar-kux' } it "includes data-lang-params tag with extra information" do result = filter(%{
This is a test
}) expect(result.to_html).to eq(%{
This is a test
}) end include_examples "XSS prevention", lang include_examples "XSS prevention", "#{lang}#{described_class::PARAMS_DELIMITER}<script>alert(1)</script>" include_examples "XSS prevention", "#{lang}#{described_class::PARAMS_DELIMITER}" end end context 'when multiple param delimiters are used' do let(:lang) { 'suggestion' } let(:lang_params) { '-1+10' } it "delimits on the first appearance" do result = filter(%{
This is a test
}) expect(result.to_html).to eq(%{
This is a test
}) end end end context "when Rouge lexing fails" do before do allow_any_instance_of(Rouge::Lexers::Ruby).to receive(:stream_tokens).and_raise(StandardError) end it "highlights as plaintext" do result = filter('
This is a test
') expect(result.to_html).to eq('
This is a test
') end include_examples "XSS prevention", "ruby" end context "when Rouge lexing fails after a retry" do before do allow_any_instance_of(Rouge::Lexers::PlainText).to receive(:stream_tokens).and_raise(StandardError) end it "does not add highlighting classes" do result = filter('
This is a test
') expect(result.to_html).to eq('
This is a test
') end include_examples "XSS prevention", "ruby" end end