jsduck 4.0.1 → 4.1.1
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.
- data/Rakefile +14 -0
- data/esprima/esprima.js +210 -85
- data/jsduck.gemspec +3 -3
- data/lib/jsduck/accessors.rb +10 -8
- data/lib/jsduck/aggregator.rb +7 -7
- data/lib/jsduck/app.rb +24 -164
- data/lib/jsduck/app_data.rb +2 -4
- data/lib/jsduck/assets.rb +5 -2
- data/lib/jsduck/ast.rb +9 -4
- data/lib/jsduck/batch_formatter.rb +54 -0
- data/lib/jsduck/batch_parser.rb +106 -0
- data/lib/jsduck/categories.rb +5 -6
- data/lib/jsduck/class.rb +77 -239
- data/lib/jsduck/class_doc_expander.rb +0 -5
- data/lib/jsduck/class_formatter.rb +14 -10
- data/lib/jsduck/class_name.rb +23 -0
- data/lib/jsduck/class_writer.rb +9 -8
- data/lib/jsduck/doc_ast.rb +5 -6
- data/lib/jsduck/doc_formatter.rb +61 -272
- data/lib/jsduck/enum.rb +4 -4
- data/lib/jsduck/esprima.rb +10 -4
- data/lib/jsduck/examples.rb +5 -5
- data/lib/jsduck/export_writer.rb +62 -0
- data/lib/jsduck/exporter/app.rb +62 -0
- data/lib/jsduck/exporter/examples.rb +58 -0
- data/lib/jsduck/exporter/full.rb +60 -0
- data/lib/jsduck/file_categories.rb +7 -4
- data/lib/jsduck/function_ast.rb +99 -0
- data/lib/jsduck/grouped_asset.rb +27 -16
- data/lib/jsduck/guide_writer.rb +8 -7
- data/lib/jsduck/guides.rb +31 -29
- data/lib/jsduck/icons.rb +12 -1
- data/lib/jsduck/images.rb +3 -3
- data/lib/jsduck/importer.rb +7 -7
- data/lib/jsduck/index_html.rb +20 -6
- data/lib/jsduck/inherit_doc.rb +9 -12
- data/lib/jsduck/inline/example.rb +42 -0
- data/lib/jsduck/inline/img.rb +55 -0
- data/lib/jsduck/inline/link.rb +227 -0
- data/lib/jsduck/inline/video.rb +67 -0
- data/lib/jsduck/inline_examples.rb +7 -7
- data/lib/jsduck/js_parser.rb +5 -4
- data/lib/jsduck/lint.rb +14 -2
- data/lib/jsduck/logger.rb +5 -6
- data/lib/jsduck/members_index.rb +132 -0
- data/lib/jsduck/merger.rb +3 -9
- data/lib/jsduck/options.rb +39 -41
- data/lib/jsduck/override.rb +3 -7
- data/lib/jsduck/relations.rb +9 -9
- data/lib/jsduck/renderer.rb +3 -3
- data/lib/jsduck/return_values.rb +72 -0
- data/lib/jsduck/search_data.rb +16 -20
- data/lib/jsduck/shortener.rb +58 -0
- data/lib/jsduck/signature_renderer.rb +1 -2
- data/lib/jsduck/source/file.rb +98 -0
- data/lib/jsduck/source/file_parser.rb +72 -0
- data/lib/jsduck/source/writer.rb +89 -0
- data/lib/jsduck/tag/aside.rb +1 -1
- data/lib/jsduck/tag/since.rb +1 -1
- data/lib/jsduck/template_dir.rb +2 -2
- data/lib/jsduck/util/html.rb +27 -0
- data/lib/jsduck/util/io.rb +32 -0
- data/lib/jsduck/util/json.rb +60 -0
- data/lib/jsduck/util/null_object.rb +23 -0
- data/lib/jsduck/util/os.rb +14 -0
- data/lib/jsduck/util/parallel.rb +34 -0
- data/lib/jsduck/util/singleton.rb +35 -0
- data/lib/jsduck/util/stdout.rb +33 -0
- data/lib/jsduck/videos.rb +5 -5
- data/lib/jsduck/web_writer.rb +79 -0
- data/lib/jsduck/welcome.rb +6 -6
- data/spec/class_factory.rb +20 -0
- metadata +32 -20
- data/lib/jsduck/api_exporter.rb +0 -48
- data/lib/jsduck/app_exporter.rb +0 -60
- data/lib/jsduck/examples_exporter.rb +0 -56
- data/lib/jsduck/full_exporter.rb +0 -35
- data/lib/jsduck/html.rb +0 -25
- data/lib/jsduck/inline_img.rb +0 -53
- data/lib/jsduck/inline_video.rb +0 -58
- data/lib/jsduck/io.rb +0 -30
- data/lib/jsduck/json_duck.rb +0 -52
- data/lib/jsduck/lexer.rb +0 -251
- data/lib/jsduck/null_object.rb +0 -19
- data/lib/jsduck/os.rb +0 -11
- data/lib/jsduck/parallel_wrap.rb +0 -32
- data/lib/jsduck/source_file.rb +0 -97
- data/lib/jsduck/source_file_parser.rb +0 -70
- data/lib/jsduck/source_writer.rb +0 -87
- data/lib/jsduck/stats.rb +0 -103
- data/lib/jsduck/stdout.rb +0 -31
@@ -0,0 +1,42 @@
|
|
1
|
+
module JsDuck
|
2
|
+
module Inline
|
3
|
+
|
4
|
+
# Implementation of @example tag.
|
5
|
+
#
|
6
|
+
# Looks for @example tag at the beginning of code blocks. When
|
7
|
+
# found, adds an "inline-example" CSS class to the <pre> element.
|
8
|
+
#
|
9
|
+
# Unlike other Inline:: classes this doesn't implement an
|
10
|
+
# {@example} tag as could be expected. But it fits nicely along
|
11
|
+
# with other inline tags as it's processed inside DocFormatter, so
|
12
|
+
# it mostly fits here along with the others.
|
13
|
+
#
|
14
|
+
class Example
|
15
|
+
# Constructor takes opts parameter for consistency with other
|
16
|
+
# JsDuck::Inline::* classes.
|
17
|
+
def initialize(opts={})
|
18
|
+
@re = /<pre><code>\s*@example( +[^\n]*)?\s+/m
|
19
|
+
end
|
20
|
+
|
21
|
+
# Takes StringScanner instance.
|
22
|
+
#
|
23
|
+
# Looks for "<pre><code>@example" at the current scan pointer
|
24
|
+
# position, when found, moves scan pointer forward and performs
|
25
|
+
# the apporpriate replacement.
|
26
|
+
def replace(input)
|
27
|
+
if input.check(@re)
|
28
|
+
# Match possible classnames following @example and add them
|
29
|
+
# as CSS classes inside <pre> element.
|
30
|
+
input.scan(@re) =~ @re
|
31
|
+
css_classes = ($1 || "").strip
|
32
|
+
|
33
|
+
return "<pre class='inline-example #{css_classes}'><code>"
|
34
|
+
else
|
35
|
+
false
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
require 'jsduck/util/html'
|
2
|
+
require 'jsduck/logger'
|
3
|
+
|
4
|
+
module JsDuck
|
5
|
+
module Inline
|
6
|
+
|
7
|
+
# Implementation of inline tag {@img}
|
8
|
+
class Img
|
9
|
+
# Base path to prefix images from {@img} tags.
|
10
|
+
# Defaults to no prefix.
|
11
|
+
attr_accessor :base_path
|
12
|
+
|
13
|
+
# This will hold list of all image paths gathered from {@img} tags.
|
14
|
+
attr_accessor :images
|
15
|
+
|
16
|
+
def initialize(opts={})
|
17
|
+
@tpl = opts[:img_tpl] || '<img src="%u" alt="%a"/>'
|
18
|
+
|
19
|
+
@re = /\{@img\s+(\S*?)(?:\s+(.+?))?\}/m
|
20
|
+
|
21
|
+
@base_path = nil
|
22
|
+
@images = []
|
23
|
+
end
|
24
|
+
|
25
|
+
# Takes StringScanner instance.
|
26
|
+
#
|
27
|
+
# Looks for inline tag at the current scan pointer position, when
|
28
|
+
# found, moves scan pointer forward and performs the apporpriate
|
29
|
+
# replacement.
|
30
|
+
def replace(input)
|
31
|
+
if input.check(@re)
|
32
|
+
input.scan(@re).sub(@re) { apply_tpl($1, $2) }
|
33
|
+
else
|
34
|
+
false
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
# applies the image template
|
39
|
+
def apply_tpl(url, alt_text)
|
40
|
+
@images << url
|
41
|
+
@tpl.gsub(/(%\w)/) do
|
42
|
+
case $1
|
43
|
+
when '%u'
|
44
|
+
@base_path ? (@base_path + "/" + url) : url
|
45
|
+
when '%a'
|
46
|
+
Util::HTML.escape(alt_text||"")
|
47
|
+
else
|
48
|
+
$1
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,227 @@
|
|
1
|
+
require 'jsduck/util/html'
|
2
|
+
require 'jsduck/logger'
|
3
|
+
|
4
|
+
module JsDuck
|
5
|
+
module Inline
|
6
|
+
|
7
|
+
# Implementation of inline tag {@link}
|
8
|
+
#
|
9
|
+
# It also takes care of the auto-detection of links in text
|
10
|
+
# through the #create_magic_links method.
|
11
|
+
class Link
|
12
|
+
# Sets up instance to work in context of particular class, so
|
13
|
+
# that when {@link #blah} is encountered it knows that
|
14
|
+
# Context#blah is meant.
|
15
|
+
attr_accessor :class_context
|
16
|
+
|
17
|
+
# Sets up instance to work in context of particular doc object.
|
18
|
+
# Used for error reporting.
|
19
|
+
attr_accessor :doc_context
|
20
|
+
|
21
|
+
# JsDuck::Relations for looking up class names.
|
22
|
+
#
|
23
|
+
# When auto-creating class links from CamelCased names found from
|
24
|
+
# text, we check the relations object to see if a class with that
|
25
|
+
# name actually exists.
|
26
|
+
attr_accessor :relations
|
27
|
+
|
28
|
+
def initialize(opts={})
|
29
|
+
@class_context = ""
|
30
|
+
@doc_context = {}
|
31
|
+
@relations = {}
|
32
|
+
|
33
|
+
# Template HTML that replaces {@link Class#member anchor text}.
|
34
|
+
# Can contain placeholders:
|
35
|
+
#
|
36
|
+
# %c - full class name (e.g. "Ext.Panel")
|
37
|
+
# %m - class member name prefixed with member type (e.g. "method-urlEncode")
|
38
|
+
# %# - inserts "#" if member name present
|
39
|
+
# %- - inserts "-" if member name present
|
40
|
+
# %a - anchor text for link
|
41
|
+
@tpl = opts[:link_tpl] || '<a href="%c%#%m">%a</a>'
|
42
|
+
|
43
|
+
@re = /\{@link\s+(\S*?)(?:\s+(.+?))?\}/m
|
44
|
+
end
|
45
|
+
|
46
|
+
# Takes StringScanner instance.
|
47
|
+
#
|
48
|
+
# Looks for inline tag at the current scan pointer position, when
|
49
|
+
# found, moves scan pointer forward and performs the apporpriate
|
50
|
+
# replacement.
|
51
|
+
def replace(input)
|
52
|
+
if input.check(@re)
|
53
|
+
input.scan(@re).sub(@re) { apply_tpl($1, $2, $&) }
|
54
|
+
else
|
55
|
+
false
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
# applies the link template
|
60
|
+
def apply_tpl(target, text, full_link)
|
61
|
+
if target =~ /^(.*)#(static-)?(?:(cfg|property|method|event|css_var|css_mixin)-)?(.*)$/
|
62
|
+
cls = $1.empty? ? @class_context : $1
|
63
|
+
static = $2 ? true : nil
|
64
|
+
type = $3 ? $3.intern : nil
|
65
|
+
member = $4
|
66
|
+
else
|
67
|
+
cls = target
|
68
|
+
static = nil
|
69
|
+
type = false
|
70
|
+
member = false
|
71
|
+
end
|
72
|
+
|
73
|
+
# Construct link text
|
74
|
+
if text
|
75
|
+
text = text
|
76
|
+
elsif member
|
77
|
+
text = (cls == @class_context) ? member : (cls + "." + member)
|
78
|
+
else
|
79
|
+
text = cls
|
80
|
+
end
|
81
|
+
|
82
|
+
file = @doc_context[:filename]
|
83
|
+
line = @doc_context[:linenr]
|
84
|
+
if !@relations[cls]
|
85
|
+
Logger.warn(:link, "#{full_link} links to non-existing class", file, line)
|
86
|
+
return text
|
87
|
+
elsif member
|
88
|
+
ms = find_members(cls, {:name => member, :tagname => type, :static => static})
|
89
|
+
if ms.length == 0
|
90
|
+
Logger.warn(:link, "#{full_link} links to non-existing member", file, line)
|
91
|
+
return text
|
92
|
+
end
|
93
|
+
|
94
|
+
if ms.length > 1
|
95
|
+
# When multiple public members, see if there remains just
|
96
|
+
# one when we ignore the static members. If there's more,
|
97
|
+
# report ambiguity. If there's only static members, also
|
98
|
+
# report ambiguity.
|
99
|
+
instance_ms = ms.find_all {|m| !m[:meta][:static] }
|
100
|
+
if instance_ms.length > 1
|
101
|
+
alternatives = instance_ms.map {|m| "#{m[:tagname]} in #{m[:owner]}" }.join(", ")
|
102
|
+
Logger.warn(:link_ambiguous, "#{full_link} is ambiguous: "+alternatives, file, line)
|
103
|
+
elsif instance_ms.length == 0
|
104
|
+
static_ms = ms.find_all {|m| m[:meta][:static] }
|
105
|
+
alternatives = static_ms.map {|m| "static " + m[:tagname].to_s }.join(", ")
|
106
|
+
Logger.warn(:link_ambiguous, "#{full_link} is ambiguous: "+alternatives, file, line)
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
return link(cls, member, text, type, static)
|
111
|
+
else
|
112
|
+
return link(cls, false, text)
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
116
|
+
# Looks input text for patterns like:
|
117
|
+
#
|
118
|
+
# My.ClassName
|
119
|
+
# MyClass#method
|
120
|
+
# #someProperty
|
121
|
+
#
|
122
|
+
# and converts them to links, as if they were surrounded with
|
123
|
+
# {@link} tag. One notable exception is that Foo is not created to
|
124
|
+
# link, even when Foo class exists, but Foo.Bar is. This is to
|
125
|
+
# avoid turning normal words into links. For example:
|
126
|
+
#
|
127
|
+
# Math involves a lot of numbers. Ext JS is a JavaScript framework.
|
128
|
+
#
|
129
|
+
# In these sentences we don't want to link "Math" and "Ext" to the
|
130
|
+
# corresponding JS classes. And that's why we auto-link only
|
131
|
+
# class names containing a dot "."
|
132
|
+
#
|
133
|
+
def create_magic_links(input)
|
134
|
+
cls_re = "([A-Z][A-Za-z0-9.]*[A-Za-z0-9])"
|
135
|
+
member_re = "(?:#([A-Za-z0-9]+))"
|
136
|
+
|
137
|
+
input.gsub(/\b#{cls_re}#{member_re}?\b|#{member_re}\b/m) do
|
138
|
+
replace_magic_link($1, $2 || $3)
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
def replace_magic_link(cls, member)
|
143
|
+
if cls && member
|
144
|
+
if @relations[cls] && get_matching_member(cls, {:name => member})
|
145
|
+
return link(cls, member, cls+"."+member)
|
146
|
+
else
|
147
|
+
warn_magic_link("#{cls}##{member} links to non-existing " + (@relations[cls] ? "member" : "class"))
|
148
|
+
end
|
149
|
+
elsif cls && cls =~ /\./
|
150
|
+
if @relations[cls]
|
151
|
+
return link(cls, nil, cls)
|
152
|
+
else
|
153
|
+
cls2, member2 = split_to_cls_and_member(cls)
|
154
|
+
if @relations[cls2] && get_matching_member(cls2, {:name => member2})
|
155
|
+
return link(cls2, member2, cls2+"."+member2)
|
156
|
+
elsif cls =~ /\.(js|css|html|php)\Z/
|
157
|
+
# Ignore common filenames
|
158
|
+
else
|
159
|
+
warn_magic_link("#{cls} links to non-existing class")
|
160
|
+
end
|
161
|
+
end
|
162
|
+
elsif !cls && member
|
163
|
+
if get_matching_member(@class_context, {:name => member})
|
164
|
+
return link(@class_context, member, member)
|
165
|
+
elsif member =~ /\A([A-F0-9]{3}|[A-F0-9]{6})\Z/i || member =~ /\A[0-9]/
|
166
|
+
# Ignore HEX color codes and
|
167
|
+
# member names beginning with number
|
168
|
+
else
|
169
|
+
warn_magic_link("##{member} links to non-existing member")
|
170
|
+
end
|
171
|
+
end
|
172
|
+
|
173
|
+
return "#{cls}#{member ? '#' : ''}#{member}"
|
174
|
+
end
|
175
|
+
|
176
|
+
def split_to_cls_and_member(str)
|
177
|
+
parts = str.split(/\./)
|
178
|
+
return [parts.slice(0, parts.length-1).join("."), parts.last]
|
179
|
+
end
|
180
|
+
|
181
|
+
def warn_magic_link(msg)
|
182
|
+
Logger.warn(:link_auto, msg, @doc_context[:filename], @doc_context[:linenr])
|
183
|
+
end
|
184
|
+
|
185
|
+
# applies the link template
|
186
|
+
def link(cls, member, anchor_text, type=nil, static=nil)
|
187
|
+
# Use the canonical class name for link (not some alternateClassName)
|
188
|
+
cls = @relations[cls][:name]
|
189
|
+
# prepend type name to member name
|
190
|
+
member = member && get_matching_member(cls, {:name => member, :tagname => type, :static => static})
|
191
|
+
|
192
|
+
@tpl.gsub(/(%[\w#-])/) do
|
193
|
+
case $1
|
194
|
+
when '%c'
|
195
|
+
cls
|
196
|
+
when '%m'
|
197
|
+
member ? member[:id] : ""
|
198
|
+
when '%#'
|
199
|
+
member ? "#" : ""
|
200
|
+
when '%-'
|
201
|
+
member ? "-" : ""
|
202
|
+
when '%a'
|
203
|
+
Util::HTML.escape(anchor_text||"")
|
204
|
+
else
|
205
|
+
$1
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
209
|
+
|
210
|
+
def get_matching_member(cls, query)
|
211
|
+
ms = find_members(cls, query).find_all {|m| !m[:private] }
|
212
|
+
if ms.length > 1
|
213
|
+
instance_ms = ms.find_all {|m| !m[:meta][:static] }
|
214
|
+
instance_ms.length > 0 ? instance_ms[0] : ms.find_all {|m| m[:meta][:static] }[0]
|
215
|
+
else
|
216
|
+
ms[0]
|
217
|
+
end
|
218
|
+
end
|
219
|
+
|
220
|
+
def find_members(cls, query)
|
221
|
+
@relations[cls] ? @relations[cls].find_members(query) : []
|
222
|
+
end
|
223
|
+
|
224
|
+
end
|
225
|
+
|
226
|
+
end
|
227
|
+
end
|
@@ -0,0 +1,67 @@
|
|
1
|
+
require 'jsduck/util/html'
|
2
|
+
require 'jsduck/logger'
|
3
|
+
|
4
|
+
module JsDuck
|
5
|
+
module Inline
|
6
|
+
|
7
|
+
# Implementation of inline tag {@video}
|
8
|
+
class Video
|
9
|
+
# Sets up instance to work in context of particular doc object.
|
10
|
+
# Used for error reporting.
|
11
|
+
attr_accessor :doc_context
|
12
|
+
|
13
|
+
def initialize(opts={})
|
14
|
+
@doc_context = {}
|
15
|
+
|
16
|
+
@templates = {
|
17
|
+
"html5" => '<video src="%u">%a</video>',
|
18
|
+
"vimeo" => [
|
19
|
+
'<p><object width="640" height="360">',
|
20
|
+
'<param name="allowfullscreen" value="true" />',
|
21
|
+
'<param name="allowscriptaccess" value="always" />',
|
22
|
+
'<param name="flashvars" value="api=1" />',
|
23
|
+
'<param name="movie" value="http://vimeo.com/moogaloop.swf?clip_id=%u&server=vimeo.com&color=4CC208&fullscreen=1" />',
|
24
|
+
'<embed src="http://vimeo.com/moogaloop.swf?clip_id=%u&server=vimeo.com&color=4CC208&fullscreen=1" ',
|
25
|
+
'type="application/x-shockwave-flash" allowfullscreen="true" allowscriptaccess="always" width="640" height="360"></embed>',
|
26
|
+
'</object></p>',
|
27
|
+
].join
|
28
|
+
}
|
29
|
+
|
30
|
+
@re = /\{@video\s+(\w+)\s+(\S*?)(?:\s+(.+?))?\}/m
|
31
|
+
end
|
32
|
+
|
33
|
+
# Takes StringScanner instance.
|
34
|
+
#
|
35
|
+
# Looks for inline tag at the current scan pointer position, when
|
36
|
+
# found, moves scan pointer forward and performs the apporpriate
|
37
|
+
# replacement.
|
38
|
+
def replace(input)
|
39
|
+
if input.check(@re)
|
40
|
+
input.scan(@re).sub(@re) { apply_tpl($1, $2, $3) }
|
41
|
+
else
|
42
|
+
false
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
# applies the video template of the specified type
|
47
|
+
def apply_tpl(type, url, alt_text)
|
48
|
+
unless @templates.has_key?(type)
|
49
|
+
ctx = @doc_context
|
50
|
+
Logger.warn(nil, "Unknown video type #{type}", ctx[:filename], ctx[:linenr])
|
51
|
+
end
|
52
|
+
|
53
|
+
@templates[type].gsub(/(%\w)/) do
|
54
|
+
case $1
|
55
|
+
when '%u'
|
56
|
+
url
|
57
|
+
when '%a'
|
58
|
+
Util::HTML.escape(alt_text||"")
|
59
|
+
else
|
60
|
+
$1
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
end
|
67
|
+
end
|
@@ -1,5 +1,5 @@
|
|
1
|
-
require 'jsduck/
|
2
|
-
require 'jsduck/html'
|
1
|
+
require 'jsduck/util/json'
|
2
|
+
require 'jsduck/util/html'
|
3
3
|
|
4
4
|
module JsDuck
|
5
5
|
|
@@ -16,9 +16,9 @@ module JsDuck
|
|
16
16
|
relations.each do |cls|
|
17
17
|
extract(cls[:doc]).each_with_index do |ex, i|
|
18
18
|
@examples << {
|
19
|
-
:id => cls
|
20
|
-
:name => cls
|
21
|
-
:href => '#!/api/' + cls
|
19
|
+
:id => cls[:name] + "-" + i.to_s,
|
20
|
+
:name => cls[:name] + " example #" + (i+1).to_s,
|
21
|
+
:href => '#!/api/' + cls[:name],
|
22
22
|
:code => ex[:code],
|
23
23
|
:options => ex[:options],
|
24
24
|
}
|
@@ -47,7 +47,7 @@ module JsDuck
|
|
47
47
|
|
48
48
|
# Writes all found examples to .js file
|
49
49
|
def write(filename)
|
50
|
-
|
50
|
+
Util::Json.write_jsonp(filename, "__inline_examples__", @examples)
|
51
51
|
end
|
52
52
|
|
53
53
|
# Extracts inline examples from HTML
|
@@ -65,7 +65,7 @@ module JsDuck
|
|
65
65
|
ex = s.scan_until(@end_example_re).sub(@end_example_re, '')
|
66
66
|
|
67
67
|
examples << {
|
68
|
-
:code => HTML.unescape(HTML.strip_tags(ex)),
|
68
|
+
:code => Util::HTML.unescape(Util::HTML.strip_tags(ex)),
|
69
69
|
:options => options,
|
70
70
|
}
|
71
71
|
else
|
data/lib/jsduck/js_parser.rb
CHANGED
@@ -25,7 +25,7 @@ module JsDuck
|
|
25
25
|
# }
|
26
26
|
#
|
27
27
|
def parse
|
28
|
-
@ast = Esprima.
|
28
|
+
@ast = Esprima.parse(@input)
|
29
29
|
|
30
30
|
@ast["comments"] = merge_comments(@ast["comments"])
|
31
31
|
locate_comments
|
@@ -62,10 +62,11 @@ module JsDuck
|
|
62
62
|
end
|
63
63
|
|
64
64
|
# Two comments can be merged if they are both line-comments and
|
65
|
-
# they are separated only by whitespace (
|
65
|
+
# they are separated only by whitespace (only one newline at the
|
66
|
+
# end of the first comment is allowed)
|
66
67
|
def mergeable?(c1, c2)
|
67
68
|
if c1["type"] == "Line" && c2["type"] == "Line"
|
68
|
-
/\A[ \t]*\Z/ =~ @input.slice((c1["range"][1])..(c2["range"][0]-1))
|
69
|
+
/\A(\r\n|\n|\r)?[ \t]*\Z/ =~ @input.slice((c1["range"][1])..(c2["range"][0]-1))
|
69
70
|
else
|
70
71
|
false
|
71
72
|
end
|
@@ -156,7 +157,7 @@ module JsDuck
|
|
156
157
|
properties = NODE_TYPES[node["type"]]
|
157
158
|
|
158
159
|
unless properties
|
159
|
-
Logger.
|
160
|
+
Logger.fatal("Unknown node type: "+node["type"])
|
160
161
|
exit(1)
|
161
162
|
end
|
162
163
|
|