# frozen_string_literal: true require 'rubygems/test_case' require 'rubygems/request_set' require 'rubygems/request_set/lockfile' require 'rubygems/request_set/lockfile/tokenizer' require 'rubygems/request_set/lockfile/parser' class TestGemRequestSetLockfileTokenizer < Gem::TestCase def setup super @gem_deps_file = 'gem.deps.rb' @lock_file = File.expand_path "#{@gem_deps_file}.lock" end def test_peek tokenizer = Gem::RequestSet::Lockfile::Tokenizer.new "\n" assert_equal :newline, tokenizer.peek.first assert_equal :newline, tokenizer.next_token.first assert_equal :EOF, tokenizer.peek.first end def test_skip tokenizer = Gem::RequestSet::Lockfile::Tokenizer.new "\n" refute_predicate tokenizer, :empty? tokenizer.skip :newline assert_empty tokenizer end def test_token_pos tokenizer = Gem::RequestSet::Lockfile::Tokenizer.new '' assert_equal [5, 0], tokenizer.token_pos(5) tokenizer = Gem::RequestSet::Lockfile::Tokenizer.new '', nil, 1, 2 assert_equal [3, 1], tokenizer.token_pos(5) end def test_tokenize write_lockfile <<-LOCKFILE GEM remote: #{@gem_repo} specs: a (2) b (= 2) c (!= 3) d (> 4) e (< 5) f (>= 6) g (<= 7) h (~> 8) PLATFORMS #{Gem::Platform::RUBY} DEPENDENCIES a LOCKFILE expected = [ [:section, 'GEM', 0, 0], [:newline, nil, 3, 0], [:entry, 'remote', 2, 1], [:text, @gem_repo, 10, 1], [:newline, nil, 34, 1], [:entry, 'specs', 2, 2], [:newline, nil, 8, 2], [:text, 'a', 4, 3], [:l_paren, nil, 6, 3], [:text, '2', 7, 3], [:r_paren, nil, 8, 3], [:newline, nil, 9, 3], [:text, 'b', 6, 4], [:l_paren, nil, 8, 4], [:requirement, '=', 9, 4], [:text, '2', 11, 4], [:r_paren, nil, 12, 4], [:newline, nil, 13, 4], [:text, 'c', 6, 5], [:l_paren, nil, 8, 5], [:requirement, '!=', 9, 5], [:text, '3', 12, 5], [:r_paren, nil, 13, 5], [:newline, nil, 14, 5], [:text, 'd', 6, 6], [:l_paren, nil, 8, 6], [:requirement, '>', 9, 6], [:text, '4', 11, 6], [:r_paren, nil, 12, 6], [:newline, nil, 13, 6], [:text, 'e', 6, 7], [:l_paren, nil, 8, 7], [:requirement, '<', 9, 7], [:text, '5', 11, 7], [:r_paren, nil, 12, 7], [:newline, nil, 13, 7], [:text, 'f', 6, 8], [:l_paren, nil, 8, 8], [:requirement, '>=', 9, 8], [:text, '6', 12, 8], [:r_paren, nil, 13, 8], [:newline, nil, 14, 8], [:text, 'g', 6, 9], [:l_paren, nil, 8, 9], [:requirement, '<=', 9, 9], [:text, '7', 12, 9], [:r_paren, nil, 13, 9], [:newline, nil, 14, 9], [:text, 'h', 6, 10], [:l_paren, nil, 8, 10], [:requirement, '~>', 9, 10], [:text, '8', 12, 10], [:r_paren, nil, 13, 10], [:newline, nil, 14, 10], [:newline, nil, 0, 11], [:section, 'PLATFORMS', 0, 12], [:newline, nil, 9, 12], [:text, Gem::Platform::RUBY, 2, 13], [:newline, nil, 6, 13], [:newline, nil, 0, 14], [:section, 'DEPENDENCIES', 0, 15], [:newline, nil, 12, 15], [:text, 'a', 2, 16], [:newline, nil, 3, 16], ] assert_equal expected, tokenize_lockfile end def test_tokenize_capitals write_lockfile <<-LOCKFILE GEM remote: #{@gem_repo} specs: Ab (2) PLATFORMS #{Gem::Platform::RUBY} DEPENDENCIES Ab LOCKFILE expected = [ [:section, 'GEM', 0, 0], [:newline, nil, 3, 0], [:entry, 'remote', 2, 1], [:text, @gem_repo, 10, 1], [:newline, nil, 34, 1], [:entry, 'specs', 2, 2], [:newline, nil, 8, 2], [:text, 'Ab', 4, 3], [:l_paren, nil, 7, 3], [:text, '2', 8, 3], [:r_paren, nil, 9, 3], [:newline, nil, 10, 3], [:newline, nil, 0, 4], [:section, 'PLATFORMS', 0, 5], [:newline, nil, 9, 5], [:text, Gem::Platform::RUBY, 2, 6], [:newline, nil, 6, 6], [:newline, nil, 0, 7], [:section, 'DEPENDENCIES', 0, 8], [:newline, nil, 12, 8], [:text, 'Ab', 2, 9], [:newline, nil, 4, 9], ] assert_equal expected, tokenize_lockfile end def test_tokenize_conflict_markers write_lockfile '<<<<<<<' e = assert_raises Gem::RequestSet::Lockfile::ParseError do tokenize_lockfile end assert_equal "your #{@lock_file} contains merge conflict markers (at line 0 column 0)", e.message write_lockfile '|||||||' e = assert_raises Gem::RequestSet::Lockfile::ParseError do tokenize_lockfile end assert_equal "your #{@lock_file} contains merge conflict markers (at line 0 column 0)", e.message write_lockfile '=======' e = assert_raises Gem::RequestSet::Lockfile::ParseError do tokenize_lockfile end assert_equal "your #{@lock_file} contains merge conflict markers (at line 0 column 0)", e.message write_lockfile '>>>>>>>' e = assert_raises Gem::RequestSet::Lockfile::ParseError do tokenize_lockfile end assert_equal "your #{@lock_file} contains merge conflict markers (at line 0 column 0)", e.message end def test_tokenize_git write_lockfile <<-LOCKFILE DEPENDENCIES a! LOCKFILE expected = [ [:section, 'DEPENDENCIES', 0, 0], [:newline, nil, 12, 0], [:text, 'a', 2, 1], [:bang, nil, 3, 1], [:newline, nil, 4, 1], ] assert_equal expected, tokenize_lockfile end def test_tokenize_multiple write_lockfile <<-LOCKFILE GEM remote: #{@gem_repo} specs: a (2) b (~> 3.0, >= 3.0.1) LOCKFILE expected = [ [:section, 'GEM', 0, 0], [:newline, nil, 3, 0], [:entry, 'remote', 2, 1], [:text, @gem_repo, 10, 1], [:newline, nil, 34, 1], [:entry, 'specs', 2, 2], [:newline, nil, 8, 2], [:text, 'a', 4, 3], [:l_paren, nil, 6, 3], [:text, '2', 7, 3], [:r_paren, nil, 8, 3], [:newline, nil, 9, 3], [:text, 'b', 6, 4], [:l_paren, nil, 8, 4], [:requirement, '~>', 9, 4], [:text, '3.0', 12, 4], [:comma, nil, 15, 4], [:requirement, '>=', 17, 4], [:text, '3.0.1', 20, 4], [:r_paren, nil, 25, 4], [:newline, nil, 26, 4], ] assert_equal expected, tokenize_lockfile end def test_unget tokenizer = Gem::RequestSet::Lockfile::Tokenizer.new "\n" tokenizer.unshift :token parser = tokenizer.make_parser nil, nil assert_equal :token, parser.get end def write_lockfile lockfile open @lock_file, 'w' do |io| io.write lockfile end end def tokenize_lockfile Gem::RequestSet::Lockfile::Tokenizer.from_file(@lock_file).to_a end end