github-markdown 0.6.6 → 0.6.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 2ead7b9ae4db02386f4f35576e957f92eb26bfbd
4
- data.tar.gz: c972c6d581bf37be2359c046274200b40f4ddb18
3
+ metadata.gz: 0e82a12c8f502be0b25a184c0d64f3f9a1b34f28
4
+ data.tar.gz: ee0fcb46a6dfacad26dae9e96fb97158b7ca5da3
5
5
  SHA512:
6
- metadata.gz: 509eb216bdd44d8dc4dad574dee402642953dce1ab43279a137f6e78f516343c00983d46cbb6b20cff4b852e5c9c90243c9bfbb22b81f99905ec6f1d7cb740dc
7
- data.tar.gz: 06873a9f7da78b90d5be14ddfcfda5331e22600b7bd4ff8bb2a467eef89ec429758f6acde3b6c639cf2b1f7e684d964f80131ddd20f788574bbeeef2c21ca261
6
+ metadata.gz: 9f46e7837ac995778eb868eca67d398ed0b2e3148854c2609ac295d5884f225dbc708603442671feec9d5deb04d875bf493a03956b7752e2a4fe52f52a7c9eff
7
+ data.tar.gz: 1cddaba6030d05ccfb0c82e178afcbfa9e29b08a790eda845cfa27a75acca8d590c74cd596446167bce8ba8ec26149b59cf295d8566ff35c6dd5eb7c8484f6ee
@@ -51,7 +51,7 @@ sd_autolink_issafe(const uint8_t *link, size_t link_len)
51
51
  static size_t
52
52
  autolink_delim(uint8_t *data, size_t link_end, size_t max_rewind, size_t size)
53
53
  {
54
- uint8_t cclose, copen = 0;
54
+ uint8_t cclose, copen;
55
55
  size_t i;
56
56
 
57
57
  for (i = 0; i < link_end; ++i)
@@ -78,20 +78,21 @@ autolink_delim(uint8_t *data, size_t link_end, size_t max_rewind, size_t size)
78
78
  else break;
79
79
  }
80
80
 
81
- if (link_end == 0)
82
- return 0;
83
-
84
- cclose = data[link_end - 1];
85
-
86
- switch (cclose) {
87
- case '"': copen = '"'; break;
88
- case '\'': copen = '\''; break;
89
- case ')': copen = '('; break;
90
- case ']': copen = '['; break;
91
- case '}': copen = '{'; break;
92
- }
81
+ while (link_end > 0) {
82
+ cclose = data[link_end - 1];
83
+
84
+ switch (cclose) {
85
+ case '"': copen = '"'; break;
86
+ case '\'': copen = '\''; break;
87
+ case ')': copen = '('; break;
88
+ case ']': copen = '['; break;
89
+ case '}': copen = '{'; break;
90
+ default: copen = 0;
91
+ }
93
92
 
94
- if (copen != 0) {
93
+ if (copen == 0)
94
+ break;
95
+
95
96
  size_t closing = 0;
96
97
  size_t opening = 0;
97
98
  size_t i = 0;
@@ -125,8 +126,10 @@ autolink_delim(uint8_t *data, size_t link_end, size_t max_rewind, size_t size)
125
126
  i++;
126
127
  }
127
128
 
128
- if (closing != opening)
129
- link_end--;
129
+ if (closing == opening)
130
+ break;
131
+
132
+ link_end--;
130
133
  }
131
134
 
132
135
  return link_end;
@@ -306,6 +306,12 @@ tag_length(uint8_t *data, size_t size, enum mkd_autolink *autolink)
306
306
 
307
307
  /* begins with a '<' optionally followed by '/', followed by letter or number */
308
308
  if (data[0] != '<') return 0;
309
+
310
+ if ((i = is_mail_autolink(data + 1, size - 1)) != 0) {
311
+ *autolink = MKDA_EMAIL;
312
+ return i + 1;
313
+ }
314
+
309
315
  i = (data[1] == '/') ? 2 : 1;
310
316
 
311
317
  if (!_isalnum(data[i]))
@@ -318,13 +324,6 @@ tag_length(uint8_t *data, size_t size, enum mkd_autolink *autolink)
318
324
  while (i < size && (_isalnum(data[i]) || data[i] == '.' || data[i] == '+' || data[i] == '-'))
319
325
  i++;
320
326
 
321
- if (i > 1 && data[i] == '@') {
322
- if ((j = is_mail_autolink(data + i, size - i)) != 0) {
323
- *autolink = MKDA_EMAIL;
324
- return i + j;
325
- }
326
- }
327
-
328
327
  if (i > 2 && data[i] == ':') {
329
328
  *autolink = MKDA_NORMAL;
330
329
  i++;
@@ -1660,7 +1659,7 @@ parse_listitem(struct buf *ob, struct sd_markdown *rndr, uint8_t *data, size_t s
1660
1659
  {
1661
1660
  struct buf *work = 0, *inter = 0;
1662
1661
  size_t beg = 0, end, pre, sublist = 0, orgpre = 0, previous_indent = 0, i;
1663
- int in_empty = 0, has_inside_empty = 0, has_trailing_empty = 0, in_fence = 0, previous_indent_diff = 0;
1662
+ int empty_lines = 0, has_inside_empty = 0, has_trailing_empty = 0, in_fence = 0, previous_indent_diff = 0;
1664
1663
 
1665
1664
  /* keeping track of the first indentation prefix */
1666
1665
  while (orgpre < 3 && orgpre < size && data[orgpre] == ' ')
@@ -1697,7 +1696,7 @@ parse_listitem(struct buf *ob, struct sd_markdown *rndr, uint8_t *data, size_t s
1697
1696
 
1698
1697
  /* process an empty line */
1699
1698
  if (is_empty(data + beg, end - beg)) {
1700
- in_empty = 1;
1699
+ empty_lines++;
1701
1700
  beg = end;
1702
1701
  continue;
1703
1702
  }
@@ -1736,19 +1735,19 @@ parse_listitem(struct buf *ob, struct sd_markdown *rndr, uint8_t *data, size_t s
1736
1735
  has_next_oli = prefix_oli(data + beg + i, end - beg - i);
1737
1736
  }
1738
1737
 
1739
- /* checking for ul/ol switch */
1740
- if (in_empty && (
1741
- ((*flags & MKD_LIST_ORDERED) && has_next_uli) ||
1742
- (!(*flags & MKD_LIST_ORDERED) && has_next_oli))){
1743
- *flags |= MKD_LI_END;
1744
- }
1745
-
1746
1738
  /* checking for a new item */
1747
1739
  if ((has_next_uli && !is_hrule(data + beg + i, end - beg - i)) || has_next_oli) {
1748
1740
  /* the following item must have the same indentation */
1749
1741
  if (pre == orgpre) {
1750
- if (in_empty)
1742
+ if (empty_lines > 0) {
1751
1743
  has_trailing_empty = 1;
1744
+
1745
+ /* checking for ul/ol switch */
1746
+ if (((*flags & MKD_LIST_ORDERED) && has_next_uli) ||
1747
+ (!(*flags & MKD_LIST_ORDERED) && has_next_oli)) {
1748
+ *flags |= MKD_LI_END;
1749
+ }
1750
+ }
1752
1751
  break;
1753
1752
  }
1754
1753
 
@@ -1759,17 +1758,18 @@ parse_listitem(struct buf *ob, struct sd_markdown *rndr, uint8_t *data, size_t s
1759
1758
  /* joining only indented stuff after empty lines;
1760
1759
  * note that now we only require 1 space of indentation
1761
1760
  * to continue a list */
1762
- if (in_empty && pre == 0) {
1761
+ if (empty_lines > 0 && pre == 0 && !in_fence) {
1763
1762
  *flags |= MKD_LI_END;
1764
1763
  break;
1765
1764
  }
1766
- else if (in_empty) {
1767
- bufputc(work, '\n');
1765
+ else if (empty_lines > 0) {
1766
+ /* preserve all the empty lines because they
1767
+ * may be meaningful inside a code block */
1768
+ for (; empty_lines > 0; empty_lines--)
1769
+ bufputc(work, '\n');
1768
1770
  has_inside_empty = 1;
1769
1771
  }
1770
1772
 
1771
- in_empty = 0;
1772
-
1773
1773
  /* adding the line without prefix into the working buffer */
1774
1774
  bufput(work, data + beg + i, end - beg - i);
1775
1775
  beg = end;
@@ -2038,8 +2038,9 @@ parse_table_row(
2038
2038
  int *col_data,
2039
2039
  int header_flag)
2040
2040
  {
2041
- size_t i = 0, col;
2041
+ size_t i = 0, j, code_end, col;
2042
2042
  struct buf *row_work = 0;
2043
+ int nb = 0, is_escaped = 0;
2043
2044
 
2044
2045
  if (!rndr->cb.table_cell || !rndr->cb.table_row)
2045
2046
  return;
@@ -2060,8 +2061,35 @@ parse_table_row(
2060
2061
 
2061
2062
  cell_start = i;
2062
2063
 
2063
- while (i < size && data[i] != '|')
2064
- i++;
2064
+ /* find the | marking the end of this cell */
2065
+ while (i < size) {
2066
+ if (!is_escaped && data[i] == '|')
2067
+ break;
2068
+
2069
+ /* find code spans because they can contain |s */
2070
+ if (!is_escaped && data[i] == '`') {
2071
+ for (nb=0; i < size && data[i] == '`'; i++)
2072
+ nb++;
2073
+
2074
+ for (j=0, code_end=i; code_end < size && j < nb; code_end++) {
2075
+ if (data[code_end] == '`') j++;
2076
+ else j = 0;
2077
+ }
2078
+
2079
+ /* bail if there's no matching delimiter */
2080
+ if (j < nb) {
2081
+ i++;
2082
+ continue;
2083
+ }
2084
+
2085
+ i = code_end;
2086
+ is_escaped = 0;
2087
+ }
2088
+ else {
2089
+ is_escaped = !is_escaped && data[i] == '\\';
2090
+ i++;
2091
+ }
2092
+ }
2065
2093
 
2066
2094
  cell_end = i - 1;
2067
2095
 
@@ -2331,11 +2359,11 @@ is_ref(const uint8_t *data, size_t beg, size_t end, size_t *last, struct link_re
2331
2359
  i++;
2332
2360
  if (i >= end || data[i] != ':') return 0;
2333
2361
  i++;
2334
- while (i < end && data[i] == ' ') i++;
2362
+ while (i < end && (data[i] == ' ' || data[i] == '\t')) i++;
2335
2363
  if (i < end && (data[i] == '\n' || data[i] == '\r')) {
2336
2364
  i++;
2337
2365
  if (i < end && data[i] == '\r' && data[i - 1] == '\n') i++; }
2338
- while (i < end && data[i] == ' ') i++;
2366
+ while (i < end && (data[i] == ' ' || data[i] == '\t')) i++;
2339
2367
  if (i >= end) return 0;
2340
2368
 
2341
2369
  /* link: whitespace-free sequence, optionally between angle brackets */
@@ -2344,14 +2372,14 @@ is_ref(const uint8_t *data, size_t beg, size_t end, size_t *last, struct link_re
2344
2372
 
2345
2373
  link_offset = i;
2346
2374
 
2347
- while (i < end && data[i] != ' ' && data[i] != '\n' && data[i] != '\r')
2375
+ while (i < end && data[i] != ' ' && data[i] != '\t' && data[i] != '\n' && data[i] != '\r')
2348
2376
  i++;
2349
2377
 
2350
2378
  if (data[i - 1] == '>') link_end = i - 1;
2351
2379
  else link_end = i;
2352
2380
 
2353
2381
  /* optional spacer: (space | tab)* (newline | '\'' | '"' | '(' ) */
2354
- while (i < end && data[i] == ' ') i++;
2382
+ while (i < end && (data[i] == ' ' || data[i] == '\t')) i++;
2355
2383
  if (i < end && data[i] != '\n' && data[i] != '\r'
2356
2384
  && data[i] != '\'' && data[i] != '"' && data[i] != '(')
2357
2385
  return 0;
@@ -2364,7 +2392,7 @@ is_ref(const uint8_t *data, size_t beg, size_t end, size_t *last, struct link_re
2364
2392
  /* optional (space|tab)* spacer after a newline */
2365
2393
  if (line_end) {
2366
2394
  i = line_end + 1;
2367
- while (i < end && data[i] == ' ') i++; }
2395
+ while (i < end && (data[i] == ' ' || data[i] == '\t')) i++; }
2368
2396
 
2369
2397
  /* optional title: any non-newline sequence enclosed in '"()
2370
2398
  alone on its line */
@@ -2380,7 +2408,7 @@ is_ref(const uint8_t *data, size_t beg, size_t end, size_t *last, struct link_re
2380
2408
  else title_end = i;
2381
2409
  /* stepping back */
2382
2410
  i -= 1;
2383
- while (i > title_offset && data[i] == ' ')
2411
+ while (i > title_offset && (data[i] == ' ' || data[i] == '\t'))
2384
2412
  i -= 1;
2385
2413
  if (i > title_offset
2386
2414
  && (data[i] == '\'' || data[i] == '"' || data[i] == ')')) {
@@ -2509,7 +2537,8 @@ sd_markdown_render(struct buf *ob, const uint8_t *document, size_t doc_size, str
2509
2537
  static const char UTF8_BOM[] = {0xEF, 0xBB, 0xBF};
2510
2538
 
2511
2539
  struct buf *text;
2512
- size_t beg, end;
2540
+ size_t beg, end, expanded_beg;
2541
+ int in_code_block = 0;
2513
2542
 
2514
2543
  text = bufnew(64);
2515
2544
  if (!text)
@@ -2530,7 +2559,7 @@ sd_markdown_render(struct buf *ob, const uint8_t *document, size_t doc_size, str
2530
2559
  beg += 3;
2531
2560
 
2532
2561
  while (beg < doc_size) /* iterating over lines */
2533
- if (is_ref(document, beg, doc_size, &end, md->refs))
2562
+ if (!in_code_block && is_ref(document, beg, doc_size, &end, md->refs))
2534
2563
  beg = end;
2535
2564
  else { /* skipping to the next line */
2536
2565
  end = beg;
@@ -2538,8 +2567,16 @@ sd_markdown_render(struct buf *ob, const uint8_t *document, size_t doc_size, str
2538
2567
  end++;
2539
2568
 
2540
2569
  /* adding the line body if present */
2541
- if (end > beg)
2570
+ if (end > beg) {
2571
+ expanded_beg = text->size;
2572
+
2542
2573
  expand_tabs(text, document + beg, end - beg);
2574
+
2575
+ /* check for a fenced code block */
2576
+ if ((md->ext_flags & MKDEXT_FENCED_CODE) != 0 &&
2577
+ is_codefence(text->data + expanded_beg, text->size - expanded_beg, NULL) != 0)
2578
+ in_code_block = !in_code_block;
2579
+ }
2543
2580
 
2544
2581
  while (end < doc_size && (document[end] == '\n' || document[end] == '\r')) {
2545
2582
  /* add one \n per newline */
@@ -1,10 +1,10 @@
1
1
  # encoding: utf-8
2
2
  Gem::Specification.new do |s|
3
3
  s.name = 'github-markdown'
4
- s.version = '0.6.6'
4
+ s.version = '0.6.7'
5
5
  s.summary = 'The Markdown parser for GitHub.com'
6
6
  s.description = 'Self-contained Markdown parser for GitHub, with all our custom extensions'
7
- s.date = '2013-10-01'
7
+ s.date = '2014-09-16'
8
8
  s.email = 'vicent@github.com'
9
9
  s.homepage = 'http://github.github.com/github-flavored-markdown/'
10
10
  s.authors = ['GitHub, Inc']
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: github-markdown
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.6
4
+ version: 0.6.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - GitHub, Inc
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2013-10-01 00:00:00.000000000 Z
11
+ date: 2014-09-16 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: Self-contained Markdown parser for GitHub, with all our custom extensions
14
14
  email: vicent@github.com
@@ -49,17 +49,17 @@ require_paths:
49
49
  - lib
50
50
  required_ruby_version: !ruby/object:Gem::Requirement
51
51
  requirements:
52
- - - '>='
52
+ - - ">="
53
53
  - !ruby/object:Gem::Version
54
54
  version: '0'
55
55
  required_rubygems_version: !ruby/object:Gem::Requirement
56
56
  requirements:
57
- - - '>='
57
+ - - ">="
58
58
  - !ruby/object:Gem::Version
59
59
  version: '0'
60
60
  requirements: []
61
61
  rubyforge_project:
62
- rubygems_version: 2.0.3
62
+ rubygems_version: 2.2.2
63
63
  signing_key:
64
64
  specification_version: 4
65
65
  summary: The Markdown parser for GitHub.com