asciidoctor 1.5.4 → 1.5.5

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of asciidoctor might be problematic. Click here for more details.

Files changed (93) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.adoc +72 -5
  3. data/CONTRIBUTING.adoc +3 -3
  4. data/Gemfile +23 -0
  5. data/README-fr.adoc +416 -0
  6. data/README-jp.adoc +395 -0
  7. data/README-zh_CN.adoc +414 -0
  8. data/README.adoc +134 -72
  9. data/asciidoctor.gemspec +49 -0
  10. data/data/locale/attributes.adoc +470 -0
  11. data/data/stylesheets/asciidoctor-default.css +6 -5
  12. data/lib/asciidoctor.rb +22 -19
  13. data/lib/asciidoctor/abstract_block.rb +20 -10
  14. data/lib/asciidoctor/abstract_node.rb +3 -14
  15. data/lib/asciidoctor/cli/invoker.rb +5 -4
  16. data/lib/asciidoctor/cli/options.rb +1 -1
  17. data/lib/asciidoctor/converter/docbook5.rb +1 -1
  18. data/lib/asciidoctor/converter/factory.rb +1 -5
  19. data/lib/asciidoctor/converter/html5.rb +36 -31
  20. data/lib/asciidoctor/converter/manpage.rb +14 -9
  21. data/lib/asciidoctor/converter/template.rb +8 -4
  22. data/lib/asciidoctor/core_ext.rb +7 -6
  23. data/lib/asciidoctor/core_ext/{string → 1.8.7/string}/chr.rb +1 -1
  24. data/lib/asciidoctor/core_ext/1.8.7/string/limit.rb +28 -0
  25. data/lib/asciidoctor/core_ext/{symbol → 1.8.7/symbol}/length.rb +1 -1
  26. data/lib/asciidoctor/core_ext/nil_or_empty.rb +23 -0
  27. data/lib/asciidoctor/core_ext/string/limit.rb +10 -0
  28. data/lib/asciidoctor/document.rb +33 -26
  29. data/lib/asciidoctor/extensions.rb +16 -16
  30. data/lib/asciidoctor/helpers.rb +1 -1
  31. data/lib/asciidoctor/list.rb +3 -0
  32. data/lib/asciidoctor/parser.rb +47 -43
  33. data/lib/asciidoctor/path_resolver.rb +3 -1
  34. data/lib/asciidoctor/reader.rb +15 -14
  35. data/lib/asciidoctor/section.rb +2 -2
  36. data/lib/asciidoctor/stylesheets.rb +2 -1
  37. data/lib/asciidoctor/substitutors.rb +44 -46
  38. data/lib/asciidoctor/table.rb +41 -38
  39. data/lib/asciidoctor/version.rb +1 -1
  40. data/man/asciidoctor.1 +11 -4
  41. data/man/asciidoctor.adoc +7 -1
  42. data/test/attributes_test.rb +52 -0
  43. data/test/blocks_test.rb +8 -8
  44. data/test/document_test.rb +13 -1
  45. data/test/extensions_test.rb +38 -0
  46. data/test/invoker_test.rb +15 -0
  47. data/test/lists_test.rb +78 -53
  48. data/test/manpage_test.rb +15 -0
  49. data/test/paths_test.rb +3 -0
  50. data/test/reader_test.rb +2 -2
  51. data/test/sections_test.rb +10 -0
  52. data/test/substitutions_test.rb +12 -6
  53. data/test/tables_test.rb +76 -2
  54. metadata +16 -45
  55. data/lib/asciidoctor/core_ext/object/nil_or_empty.rb +0 -23
  56. data/test/fixtures/asciidoc_index.txt +0 -521
  57. data/test/fixtures/basic-docinfo-footer.html +0 -6
  58. data/test/fixtures/basic-docinfo-footer.xml +0 -8
  59. data/test/fixtures/basic-docinfo.html +0 -1
  60. data/test/fixtures/basic-docinfo.xml +0 -4
  61. data/test/fixtures/basic.asciidoc +0 -5
  62. data/test/fixtures/chapter-a.adoc +0 -3
  63. data/test/fixtures/child-include.adoc +0 -5
  64. data/test/fixtures/circle.svg +0 -8
  65. data/test/fixtures/custom-backends/erb/html5/block_paragraph.html.erb +0 -6
  66. data/test/fixtures/custom-backends/haml/docbook45/block_paragraph.xml.haml +0 -6
  67. data/test/fixtures/custom-backends/haml/html5-tweaks/block_paragraph.html.haml +0 -1
  68. data/test/fixtures/custom-backends/haml/html5/block_paragraph.html.haml +0 -3
  69. data/test/fixtures/custom-backends/haml/html5/block_sidebar.html.haml +0 -5
  70. data/test/fixtures/custom-backends/slim/docbook45/block_paragraph.xml.slim +0 -6
  71. data/test/fixtures/custom-backends/slim/html5/block_paragraph.html.slim +0 -3
  72. data/test/fixtures/custom-backends/slim/html5/block_sidebar.html.slim +0 -5
  73. data/test/fixtures/custom-docinfodir/basic-docinfo.html +0 -1
  74. data/test/fixtures/custom-docinfodir/docinfo.html +0 -1
  75. data/test/fixtures/docinfo-footer.html +0 -1
  76. data/test/fixtures/docinfo-footer.xml +0 -9
  77. data/test/fixtures/docinfo.html +0 -1
  78. data/test/fixtures/docinfo.xml +0 -3
  79. data/test/fixtures/dot.gif +0 -0
  80. data/test/fixtures/encoding.asciidoc +0 -13
  81. data/test/fixtures/grandchild-include.adoc +0 -3
  82. data/test/fixtures/hello-asciidoctor.pdf +0 -0
  83. data/test/fixtures/include-file.asciidoc +0 -24
  84. data/test/fixtures/include-file.xml +0 -5
  85. data/test/fixtures/master.adoc +0 -5
  86. data/test/fixtures/parent-include-restricted.adoc +0 -5
  87. data/test/fixtures/parent-include.adoc +0 -5
  88. data/test/fixtures/sample.asciidoc +0 -26
  89. data/test/fixtures/stylesheets/custom.css +0 -3
  90. data/test/fixtures/subs-docinfo.html +0 -2
  91. data/test/fixtures/subs.adoc +0 -7
  92. data/test/fixtures/tip.gif +0 -0
  93. data/test/test_helper.rb +0 -399
@@ -189,7 +189,7 @@ module Helpers
189
189
  # Returns the String filename with leading directories removed and, if specified, the extension removed
190
190
  def self.basename(file_name, drop_extname = false)
191
191
  if drop_extname
192
- ::File.basename file_name, ((::File.extname file_name) || '')
192
+ ::File.basename file_name, (::File.extname file_name)
193
193
  else
194
194
  ::File.basename file_name
195
195
  end
@@ -43,6 +43,9 @@ end
43
43
  # Public: Methods for managing items for AsciiDoc olists, ulist, and dlists.
44
44
  class ListItem < AbstractBlock
45
45
 
46
+ # A contextual alias for the list parent node; counterpart to the items alias on List
47
+ alias :list :parent
48
+
46
49
  # Public: Get/Set the String used to mark this list item
47
50
  attr_accessor :marker
48
51
 
@@ -437,7 +437,7 @@ class Parser
437
437
  else
438
438
  block_extensions = block_macro_extensions = false
439
439
  end
440
- #parent_context = parent.is_a?(Block) ? parent.context : nil
440
+ #parent_context = Block === parent ? parent.context : nil
441
441
  in_list = ListItem === parent
442
442
  block = nil
443
443
  style = nil
@@ -523,9 +523,11 @@ class Parser
523
523
  posattrs = []
524
524
  end
525
525
 
526
- unless !style || explicit_style
526
+ # QUESTION why did we make exception for explicit style?
527
+ #if style && !explicit_style
528
+ if style
527
529
  attributes['alt'] = style if blk_ctx == :image
528
- attributes.delete('style')
530
+ attributes.delete 'style'
529
531
  style = nil
530
532
  end
531
533
 
@@ -633,7 +635,7 @@ class Parser
633
635
  elsif (match = OrderedListRx.match(this_line))
634
636
  reader.unshift_line this_line
635
637
  block = next_outline_list(reader, :olist, parent)
636
- # QUESTION move this logic to next_outline_list?
638
+ # TODO move this logic into next_outline_list
637
639
  if !attributes['style'] && !block.attributes['style']
638
640
  marker = block.items[0].marker
639
641
  if marker.start_with? '.'
@@ -641,13 +643,13 @@ class Parser
641
643
  #attributes['style'] = (ORDERED_LIST_STYLES[block.level - 1] || ORDERED_LIST_STYLES[0]).to_s
642
644
  attributes['style'] = (ORDERED_LIST_STYLES[marker.length - 1] || ORDERED_LIST_STYLES[0]).to_s
643
645
  else
644
- style = ORDERED_LIST_STYLES.detect{|s| OrderedListMarkerRxMap[s] =~ marker }
646
+ style = ORDERED_LIST_STYLES.find {|s| OrderedListMarkerRxMap[s] =~ marker }
645
647
  attributes['style'] = (style || ORDERED_LIST_STYLES[0]).to_s
646
648
  end
647
649
  end
648
650
  break
649
651
 
650
- elsif (match = DefinitionListRx.match(this_line))
652
+ elsif (match = DescriptionListRx.match(this_line))
651
653
  reader.unshift_line this_line
652
654
  block = next_labeled_list(reader, match, parent)
653
655
  break
@@ -710,7 +712,7 @@ class Parser
710
712
  adjust_indentation! lines
711
713
 
712
714
  block = Block.new(parent, :literal, :content_model => :verbatim, :source => lines, :attributes => attributes)
713
- # a literal gets special meaning inside of a definition list
715
+ # a literal gets special meaning inside of a description list
714
716
  # TODO this feels hacky, better way to distinguish from explicit literal block?
715
717
  block.set_option('listparagraph') if in_list
716
718
 
@@ -901,7 +903,7 @@ class Parser
901
903
  if block
902
904
  block.source_location = source_location if source_location
903
905
  # REVIEW seems like there is a better way to organize this wrap-up
904
- block.title = attributes['title'] unless block.title?
906
+ block.title = attributes['title'] unless block.title?
905
907
  # FIXME HACK don't hardcode logic for alt, caption and scaledwidth on images down here
906
908
  if block.context == :image
907
909
  resolved_target = attributes['target']
@@ -1034,7 +1036,7 @@ class Parser
1034
1036
  end
1035
1037
  end
1036
1038
 
1037
- # whether a block supports complex content should be a config setting
1039
+ # whether a block supports compound content should be a config setting
1038
1040
  # if terminator is false, that means the all the lines in the reader should be parsed
1039
1041
  # NOTE could invoke filter in here, before and after parsing
1040
1042
  def self.build_block(block_context, content_model, terminator, parent, reader, attributes, options = {})
@@ -1237,7 +1239,7 @@ class Parser
1237
1239
  nil
1238
1240
  end
1239
1241
 
1240
- # Internal: Parse and construct a labeled (e.g., definition) list Block from the current position of the Reader
1242
+ # Internal: Parse and construct a description list Block from the current position of the Reader
1241
1243
  #
1242
1244
  # reader - The Reader from which to retrieve the labeled list
1243
1245
  # match - The Regexp match for the head of the list
@@ -1249,7 +1251,7 @@ class Parser
1249
1251
  previous_pair = nil
1250
1252
  # allows us to capture until we find a labeled item
1251
1253
  # that uses the same delimiter (::, :::, :::: or ;;)
1252
- sibling_pattern = DefinitionListSiblingRx[match[2]]
1254
+ sibling_pattern = DescriptionListSiblingRx[match[2]]
1253
1255
 
1254
1256
  # NOTE skip the match on the first time through as we've already done it (emulates begin...while)
1255
1257
  while match || (reader.has_more_lines? && (match = sibling_pattern.match(reader.peek_line)))
@@ -1270,12 +1272,12 @@ class Parser
1270
1272
 
1271
1273
  # Internal: Parse and construct the next ListItem for the current bulleted
1272
1274
  # (unordered or ordered) list Block, callout lists included, or the next
1273
- # term ListItem and definition ListItem pair for the labeled list Block.
1275
+ # term ListItem and description ListItem pair for the labeled list Block.
1274
1276
  #
1275
1277
  # First collect and process all the lines that constitute the next list
1276
1278
  # item for the parent list (according to its type). Next, parse those lines
1277
1279
  # into blocks and associate them with the ListItem (in the case of a
1278
- # labeled list, the definition ListItem). Finally, fold the first block
1280
+ # labeled list, the description ListItem). Finally, fold the first block
1279
1281
  # into the item's text attribute according to rules described in ListItem.
1280
1282
  #
1281
1283
  # reader - The Reader from which to retrieve the next list item
@@ -1370,7 +1372,7 @@ class Parser
1370
1372
  # through all the rules that determine what comprises a list item.
1371
1373
  #
1372
1374
  # Grab lines until a sibling list item is found, or the block is broken by a
1373
- # terminator (such as a line comment). Definition lists are more greedy if
1375
+ # terminator (such as a line comment). Description lists are more greedy if
1374
1376
  # they don't have optional inline item text...they want that text
1375
1377
  #
1376
1378
  # reader - The Reader from which to retrieve the lines.
@@ -1464,7 +1466,7 @@ class Parser
1464
1466
  elsif BlockTitleRx =~ this_line || BlockAttributeLineRx =~ this_line || AttributeEntryRx =~ this_line
1465
1467
  buffer << this_line
1466
1468
  else
1467
- if nested_list_type = (within_nested_list ? [:dlist] : NESTABLE_LIST_CONTEXTS).detect {|ctx| ListRxMap[ctx] =~ this_line }
1469
+ if nested_list_type = (within_nested_list ? [:dlist] : NESTABLE_LIST_CONTEXTS).find {|ctx| ListRxMap[ctx] =~ this_line }
1468
1470
  within_nested_list = true
1469
1471
  if nested_list_type == :dlist && $~[3].nil_or_empty?
1470
1472
  # get greedy again
@@ -1494,7 +1496,7 @@ class Parser
1494
1496
  # TODO any way to combine this with the check after skipping blank lines?
1495
1497
  if is_sibling_list_item?(this_line, list_type, sibling_trait)
1496
1498
  break
1497
- elsif nested_list_type = NESTABLE_LIST_CONTEXTS.detect {|ctx| ListRxMap[ctx] =~ this_line }
1499
+ elsif nested_list_type = NESTABLE_LIST_CONTEXTS.find {|ctx| ListRxMap[ctx] =~ this_line }
1498
1500
  buffer << this_line
1499
1501
  within_nested_list = true
1500
1502
  if nested_list_type == :dlist && $~[3].nil_or_empty?
@@ -1525,7 +1527,7 @@ class Parser
1525
1527
  end
1526
1528
  else
1527
1529
  has_text = true if !this_line.empty?
1528
- if nested_list_type = (within_nested_list ? [:dlist] : NESTABLE_LIST_CONTEXTS).detect {|ctx| ListRxMap[ctx] =~ this_line }
1530
+ if nested_list_type = (within_nested_list ? [:dlist] : NESTABLE_LIST_CONTEXTS).find {|ctx| ListRxMap[ctx] =~ this_line }
1529
1531
  within_nested_list = true
1530
1532
  if nested_list_type == :dlist && $~[3].nil_or_empty?
1531
1533
  # get greedy again
@@ -1818,7 +1820,7 @@ class Parser
1818
1820
  # apply header subs and assign to document
1819
1821
  author_metadata.each do |key, val|
1820
1822
  unless document.attributes.has_key? key
1821
- document.attributes[key] = ((val.is_a? ::String) ? document.apply_header_subs(val) : val)
1823
+ document.attributes[key] = ::String === val ? (document.apply_header_subs val) : val
1822
1824
  end
1823
1825
  end
1824
1826
 
@@ -1838,7 +1840,7 @@ class Parser
1838
1840
  rev_line = reader.read_line
1839
1841
  if (match = RevisionInfoLineRx.match(rev_line))
1840
1842
  rev_metadata['revnumber'] = match[1].rstrip if match[1]
1841
- unless (component = match[2].strip) == ''
1843
+ unless (component = match[2].strip).empty?
1842
1844
  # version must begin with 'v' if date is absent
1843
1845
  if !match[1] && (component.start_with? 'v')
1844
1846
  rev_metadata['revnumber'] = component[1..-1]
@@ -1928,7 +1930,7 @@ class Parser
1928
1930
  author_entries.each_with_index do |author_entry, idx|
1929
1931
  next if author_entry.empty?
1930
1932
  key_map = {}
1931
- if idx.zero?
1933
+ if idx == 0
1932
1934
  keys.each do |key|
1933
1935
  key_map[key.to_sym] = key
1934
1936
  end
@@ -1977,7 +1979,7 @@ class Parser
1977
1979
  author_metadata[%(#{key}_1)] = author_metadata[key] if author_metadata.has_key? key
1978
1980
  end
1979
1981
  end
1980
- if idx.zero?
1982
+ if idx == 0
1981
1983
  author_metadata['authors'] = author_metadata[key_map[:author]]
1982
1984
  else
1983
1985
  author_metadata['authors'] = %(#{author_metadata['authors']}, #{author_metadata[key_map[:author]]})
@@ -2193,7 +2195,7 @@ class Parser
2193
2195
  #
2194
2196
  # Returns the String of the first marker in this number series
2195
2197
  def self.resolve_ordered_list_marker(marker, ordinal = 0, validate = false, reader = nil)
2196
- number_style = ORDERED_LIST_STYLES.detect {|s| OrderedListMarkerRxMap[s] =~ marker }
2198
+ number_style = ORDERED_LIST_STYLES.find {|s| OrderedListMarkerRxMap[s] =~ marker }
2197
2199
  expected = actual = nil
2198
2200
  case number_style
2199
2201
  when :arabic
@@ -2247,7 +2249,7 @@ class Parser
2247
2249
  # Returns a Boolean indicating whether this line is a sibling list item given
2248
2250
  # the criteria provided
2249
2251
  def self.is_sibling_list_item?(line, list_type, sibling_trait)
2250
- if sibling_trait.is_a? ::Regexp
2252
+ if ::Regexp === sibling_trait
2251
2253
  matcher = sibling_trait
2252
2254
  expected_marker = false
2253
2255
  else
@@ -2280,25 +2282,27 @@ class Parser
2280
2282
  table.assign_caption attributes.delete('caption')
2281
2283
  end
2282
2284
 
2283
- if (attributes.key? 'cols') && !(col_specs = parse_col_specs attributes['cols']).empty?
2284
- table.create_columns col_specs
2285
- explicit_col_specs = true
2285
+ if (attributes.key? 'cols') && !(colspecs = parse_colspecs attributes['cols']).empty?
2286
+ table.create_columns colspecs
2287
+ explicit_colspecs = true
2286
2288
  else
2287
- explicit_col_specs = false
2289
+ explicit_colspecs = false
2288
2290
  end
2289
2291
 
2290
2292
  skipped = table_reader.skip_blank_lines
2291
2293
 
2292
2294
  parser_ctx = Table::ParserContext.new(table_reader, table, attributes)
2295
+ skip_implicit_header = (attributes.key? 'header-option') || (attributes.key? 'noheader-option')
2293
2296
  loop_idx = -1
2294
2297
  while table_reader.has_more_lines?
2295
2298
  loop_idx += 1
2296
2299
  line = table_reader.read_line
2297
2300
 
2298
- if skipped == 0 && loop_idx.zero? && !attributes.has_key?('options') &&
2301
+ if !skip_implicit_header && skipped == 0 && loop_idx == 0 &&
2299
2302
  !(next_line = table_reader.peek_line).nil? && next_line.empty?
2300
2303
  table.has_header_option = true
2301
- table.set_option 'header'
2304
+ attributes['header-option'] = ''
2305
+ attributes['options'] = (attributes.key? 'options') ? %(#{attributes['options']},header) : 'header'
2302
2306
  end
2303
2307
 
2304
2308
  if parser_ctx.format == 'psv'
@@ -2307,10 +2311,10 @@ class Parser
2307
2311
  # push an empty cell spec if boundary at start of line
2308
2312
  parser_ctx.close_open_cell
2309
2313
  else
2310
- next_cell_spec, line = parse_cell_spec(line, :start, parser_ctx.delimiter)
2314
+ next_cellspec, line = parse_cellspec(line, :start, parser_ctx.delimiter)
2311
2315
  # if the cell spec is not null, then we're at a cell boundary
2312
- if !next_cell_spec.nil?
2313
- parser_ctx.close_open_cell next_cell_spec
2316
+ if !next_cellspec.nil?
2317
+ parser_ctx.close_open_cell next_cellspec
2314
2318
  else
2315
2319
  # QUESTION do we not advance to next line? if so, when will we if we came into this block?
2316
2320
  end
@@ -2341,14 +2345,14 @@ class Parser
2341
2345
  end
2342
2346
 
2343
2347
  if parser_ctx.format == 'psv'
2344
- next_cell_spec, cell_text = parse_cell_spec(m.pre_match, :end)
2345
- parser_ctx.push_cell_spec next_cell_spec
2348
+ next_cellspec, cell_text = parse_cellspec(m.pre_match, :end)
2349
+ parser_ctx.push_cellspec next_cellspec
2346
2350
  parser_ctx.buffer = %(#{parser_ctx.buffer}#{cell_text})
2347
2351
  else
2348
2352
  parser_ctx.buffer = %(#{parser_ctx.buffer}#{m.pre_match})
2349
2353
  end
2350
2354
 
2351
- if (line = m.post_match) == ''
2355
+ if (line = m.post_match).empty?
2352
2356
  # hack to prevent dropping empty cell found at end of line (see issue #1106)
2353
2357
  seen = false
2354
2358
  end
@@ -2380,8 +2384,8 @@ class Parser
2380
2384
  end
2381
2385
  end
2382
2386
 
2383
- unless (table.attributes['colcount'] ||= table.columns.size) == 0 || explicit_col_specs
2384
- table.assign_col_widths
2387
+ unless (table.attributes['colcount'] ||= table.columns.size) == 0 || explicit_colspecs
2388
+ table.assign_column_widths
2385
2389
  end
2386
2390
 
2387
2391
  table.partition_header_footer attributes
@@ -2400,7 +2404,7 @@ class Parser
2400
2404
  #
2401
2405
  # returns a Hash of attributes that specify how to format
2402
2406
  # and layout the cells in the table.
2403
- def self.parse_col_specs records
2407
+ def self.parse_colspecs records
2404
2408
  records = records.tr ' ', '' if records.include? ' '
2405
2409
  # check for deprecated syntax: single number, equal column spread
2406
2410
  if records == records.to_i.to_s
@@ -2410,7 +2414,7 @@ class Parser
2410
2414
  specs = []
2411
2415
  # NOTE -1 argument ensures we don't drop empty records
2412
2416
  records.split(',', -1).each {|record|
2413
- if record == ''
2417
+ if record.empty?
2414
2418
  specs << { 'width' => 1 }
2415
2419
  # TODO might want to use scan rather than this mega-regexp
2416
2420
  elsif (m = ColumnSpecRx.match(record))
@@ -2458,7 +2462,7 @@ class Parser
2458
2462
  #
2459
2463
  # returns the Hash of attributes that indicate how to layout
2460
2464
  # and style this cell in the table.
2461
- def self.parse_cell_spec(line, pos = :start, delimiter = nil)
2465
+ def self.parse_cellspec(line, pos = :start, delimiter = nil)
2462
2466
  m = nil
2463
2467
  rest = ''
2464
2468
 
@@ -2665,13 +2669,13 @@ class Parser
2665
2669
  lines.map! do |line|
2666
2670
  next line if line.empty?
2667
2671
 
2668
- if line.start_with? TAB
2669
- line.sub!(TabIndentRx) {|tabs| full_tab_space * tabs.length }
2670
- end
2672
+ # NOTE Opal has to patch this use of sub!
2673
+ line.sub!(TabIndentRx) {|tabs| full_tab_space * tabs.length } if line.start_with? TAB
2671
2674
 
2672
2675
  if line.include? TAB
2673
2676
  # keeps track of how many spaces were added to adjust offset in match data
2674
2677
  spaces_added = 0
2678
+ # NOTE Opal has to patch this use of gsub!
2675
2679
  line.gsub!(TabRx) {
2676
2680
  # calculate how many spaces this tab represents, then replace tab with spaces
2677
2681
  if (offset = ($~.begin 0) + spaces_added) % tab_size == 0
@@ -417,7 +417,7 @@ class PathResolver
417
417
  uri_prefix = nil
418
418
 
419
419
  unless start.nil_or_empty? || (is_web_root? target)
420
- target = %(#{start}#{SLASH}#{target})
420
+ target = %(#{start.chomp '/'}#{SLASH}#{target})
421
421
  if (uri_prefix = Helpers.uri_prefix target)
422
422
  target = target[uri_prefix.length..-1]
423
423
  end
@@ -448,6 +448,8 @@ class PathResolver
448
448
  end
449
449
  else
450
450
  resolved_segments << segment
451
+ # checking for empty would eliminate repeating forward slashes
452
+ #resolved_segments << segment unless segment.empty?
451
453
  end
452
454
  end
453
455
 
@@ -41,7 +41,7 @@ class Reader
41
41
  @file = @dir = nil
42
42
  @path = '<stdin>'
43
43
  @lineno = 1 # IMPORTANT lineno assignment must proceed prepare_lines call!
44
- elsif cursor.is_a? ::String
44
+ elsif ::String === cursor
45
45
  @file = cursor
46
46
  @dir, @path = ::File.split @file
47
47
  @lineno = 1 # IMPORTANT lineno assignment must proceed prepare_lines call!
@@ -84,7 +84,7 @@ class Reader
84
84
  #
85
85
  # Returns The String lines extracted from the data
86
86
  def prepare_lines data, opts = {}
87
- if data.is_a? ::String
87
+ if ::String === data
88
88
  if opts[:normalize]
89
89
  Helpers.normalize_lines_from_string data
90
90
  else
@@ -732,10 +732,10 @@ class PreprocessorReader < Reader
732
732
  skip = !@document.attributes.has_key?(target)
733
733
  when ','
734
734
  # if any attribute is defined, then don't skip
735
- skip = !target.split(',').detect {|name| @document.attributes.has_key? name }
735
+ skip = target.split(',').none? {|name| @document.attributes.has_key? name }
736
736
  when '+'
737
737
  # if any attribute is undefined, then skip
738
- skip = target.split('+').detect {|name| !@document.attributes.has_key? name }
738
+ skip = target.split('+').any? {|name| !@document.attributes.has_key? name }
739
739
  end
740
740
  when 'ifndef'
741
741
  case delimiter
@@ -744,10 +744,10 @@ class PreprocessorReader < Reader
744
744
  skip = @document.attributes.has_key?(target)
745
745
  when ','
746
746
  # if any attribute is undefined, then don't skip
747
- skip = !target.split(',').detect {|name| !@document.attributes.has_key? name }
747
+ skip = target.split(',').none? {|name| !@document.attributes.has_key? name }
748
748
  when '+'
749
749
  # if any attribute is defined, then skip
750
- skip = target.split('+').detect {|name| @document.attributes.has_key? name }
750
+ skip = target.split('+').any? {|name| @document.attributes.has_key? name }
751
751
  end
752
752
  when 'ifeval'
753
753
  # the text in brackets must match an expression
@@ -830,10 +830,11 @@ class PreprocessorReader < Reader
830
830
  # FIXME we don't want to use a link macro if we are in a verbatim context
831
831
  replace_next_line %(link:#{target}[])
832
832
  true
833
- elsif (abs_maxdepth = @maxdepth[:abs]) > 0 && @include_stack.size >= abs_maxdepth
834
- warn %(asciidoctor: ERROR: #{line_info}: maximum include depth of #{@maxdepth[:rel]} exceeded)
835
- false
836
- elsif abs_maxdepth > 0
833
+ elsif (abs_maxdepth = @maxdepth[:abs]) > 0
834
+ if @include_stack.size >= abs_maxdepth
835
+ warn %(asciidoctor: ERROR: #{line_info}: maximum include depth of #{@maxdepth[:rel]} exceeded)
836
+ return false
837
+ end
837
838
  if ::RUBY_ENGINE_OPAL
838
839
  # NOTE resolves uri relative to currently loaded document
839
840
  # NOTE we defer checking if file exists and catch the 404 error if it does not
@@ -883,7 +884,7 @@ class PreprocessorReader < Reader
883
884
  inc_lines = []
884
885
  attributes['lines'].split(DataDelimiterRx).each do |linedef|
885
886
  if linedef.include?('..')
886
- from, to = linedef.split('..').map(&:to_i)
887
+ from, to = linedef.split('..', 2).map(&:to_i)
887
888
  if to == -1
888
889
  inc_lines << from
889
890
  inc_lines << 1.0/0.0
@@ -911,7 +912,7 @@ class PreprocessorReader < Reader
911
912
  f.each_line do |l|
912
913
  inc_lineno += 1
913
914
  take = inc_lines[0]
914
- if take.is_a?(::Float) && take.infinite?
915
+ if ::Float === take && take.infinite?
915
916
  selected.push l
916
917
  inc_line_offset = inc_lineno if inc_line_offset == 0
917
918
  else
@@ -1010,7 +1011,7 @@ class PreprocessorReader < Reader
1010
1011
  # data = IO.read file
1011
1012
  # reader.push_include data, file, path
1012
1013
  #
1013
- # Returns nothing.
1014
+ # Returns this Reader object.
1014
1015
  def push_include data, file = nil, path = nil, lineno = 1, attributes = {}
1015
1016
  @include_stack << [@lines, @file, @dir, @path, @lineno, @maxdepth, @process_lines]
1016
1017
  if file
@@ -1064,7 +1065,7 @@ class PreprocessorReader < Reader
1064
1065
  @eof = false
1065
1066
  @look_ahead = 0
1066
1067
  end
1067
- nil
1068
+ self
1068
1069
  end
1069
1070
 
1070
1071
  def pop_include
@@ -87,8 +87,8 @@ class Section < AbstractBlock
87
87
  sep = @document.attributes['idseparator'] || '_'
88
88
  pre = @document.attributes['idprefix'] || '_'
89
89
  base_id = %(#{pre}#{title.downcase.gsub(InvalidSectionIdCharsRx, sep).tr_s(sep, sep).chomp(sep)})
90
- # ensure id doesn't begin with idprefix if requested it doesn't
91
- if pre.empty? && base_id.start_with?(sep)
90
+ # ensure id doesn't begin with idseparator if idprefix is empty and idseparator is not empty
91
+ if pre.empty? && !sep.empty? && base_id.start_with?(sep)
92
92
  base_id = base_id[1..-1]
93
93
  base_id = base_id[1..-1] while base_id.start_with?(sep)
94
94
  end
@@ -71,7 +71,8 @@ class Stylesheets
71
71
  def pygments_stylesheet_data style = nil
72
72
  if load_pygments
73
73
  (@pygments_stylesheet_data ||= {})[style || DEFAULT_PYGMENTS_STYLE] ||=
74
- ::Pygments.css '.listingblock .pygments', :classprefix => 'tok-', :style => (style || DEFAULT_PYGMENTS_STYLE)
74
+ (::Pygments.css '.listingblock .pygments', :classprefix => 'tok-', :style => (style || DEFAULT_PYGMENTS_STYLE)).
75
+ sub('.listingblock .pygments {', '.listingblock .pygments, .listingblock .pygments code {')
75
76
  else
76
77
  '/* Pygments styles disabled. Pygments is not available. */'
77
78
  end