lib/yard/code_objects/base.rb in yard-0.8.3 vs lib/yard/code_objects/base.rb in yard-0.8.4
- old
+ new
@@ -48,11 +48,11 @@
# Regular expression to match constant name
CONSTANTMATCH = /[A-Z]\w*/
# Regular expression to match namespaces (const A or complex path A::B)
- NAMESPACEMATCH = /(?:(?:#{NSEPQ})?#{CONSTANTMATCH})+/
+ NAMESPACEMATCH = /(?:(?:#{NSEPQ}\s*)?#{CONSTANTMATCH})+/
# Regular expression to match a method name
METHODNAMEMATCH = /[a-zA-Z_]\w*[!?=]?|[-+~]\@|<<|>>|=~|===?|<=>|[<>]=?|\*\*|[-\/+%^&*~`|]|\[\]=?/
# Regular expression to match a fully qualified method def (self.foo, Class.foo).
@@ -134,13 +134,14 @@
# source line.
#
# @return [String] a line of source
attr_accessor :signature
- # The documentation string associated with the object
+ # The non-localized documentation string associated with the object
# @return [Docstring] the documentation string
- attr_reader :docstring
+ # @since 0.8.4
+ attr_reader :base_docstring
# Marks whether or not the method is conditionally defined at runtime
# @return [Boolean] true if the method is conditionally defined at runtime
attr_accessor :dynamic
@@ -216,13 +217,12 @@
@current_file_has_comments = false
@name = name.to_sym
@source_type = :ruby
@visibility = :public
@tags = []
- @docstring = Docstring.new('', self)
- @docstring_extra = nil
- @docstring_extra_tags = nil
+ @docstrings = {}
+ @base_docstring = Docstring.new('', self)
@namespace = nil
self.namespace = namespace
yield(self) if block_given?
end
@@ -235,11 +235,11 @@
def copy_to(other)
copyable_attributes.each do |ivar|
ivar = "@#{ivar}"
other.instance_variable_set(ivar, instance_variable_get(ivar))
end
- other.docstring = docstring.to_raw
+ other.docstring = @base_docstring.to_raw
other
end
# The name of the object
# @param [Boolean] prefix whether to show a prefix. Implement
@@ -363,51 +363,52 @@
else
@source = format_source(statement.to_s)
end
end
- undef docstring
- def docstring
- return @docstring if !@docstring_extra
- case @docstring
- when Proxy
- return @docstring_extra
- when Base
- @docstring = @docstring.docstring + @docstring_extra
- @docstring.add_tag(*@docstring_extra_tags)
- @docstring_extra = nil
- @docstring_extra_tags = nil
+ # The documentation string associated with the object
+ #
+ # @param [String, I18n::Locale] locale (I18n::Locale.default)
+ # the locale of the documentation string.
+ # @return [Docstring] the documentation string
+ def docstring(locale = I18n::Locale.default)
+ if locale.nil?
+ @base_docstring.resolve_reference
+ return @base_docstring
end
- @docstring
+
+ if locale.is_a?(String)
+ locale_name = locale
+ locale = nil
+ else
+ locale_name = locale.name
+ end
+ @docstrings[locale_name] ||=
+ translate_docstring(locale || Registry.locale(locale_name))
end
# Attaches a docstring to a code object by parsing the comments attached to the statement
# and filling the {#tags} and {#docstring} methods with the parsed information.
#
# @param [String, Array<String>, Docstring] comments
# the comments attached to the code object to be parsed
# into a docstring and meta tags.
def docstring=(comments)
- if comments =~ /\A\s*\(see (\S+)\s*\)(?:\s|$)/
- path, extra = $1, $'
- @docstring_extra = Docstring.new(extra, self)
- @docstring_extra_tags = Docstring === comments ? comments.tags : []
- @docstring_extra.add_tag(*@docstring_extra_tags)
- @docstring = Proxy.new(namespace, path)
+ @docstrings.clear
+ if Docstring === comments
+ @base_docstring = comments
else
- @docstring_extra = nil
- @docstring_extra_tags = nil
- @docstring = Docstring === comments ? comments : Docstring.new(comments, self)
+ @base_docstring = Docstring.new(comments, self)
end
end
# Default type is the lowercase class name without the "Object" suffix.
# Override this method to provide a custom object type
#
# @return [Symbol] the type of code object this represents
def type
- self.class.name.split(/#{NSEPQ}/).last.gsub(/Object$/, '').downcase.to_sym
+ self.class.name.split('::').last.gsub(/Object$/, '').downcase.to_sym
end
# Represents the unique path of the object. The default implementation
# joins the path of {#namespace} with {#name} via the value of {#sep}.
# Custom code objects should ensure that the path is unique to the code
@@ -424,10 +425,20 @@
name.to_s
end
end
alias_method :to_s, :path
+ # @note
+ # Override this method if your object has a special title that does
+ # not match the {#path} attribute value. This title will be used
+ # when linking or displaying the object.
+ # @return [String] the display title for an object
+ # @see 0.8.4
+ def title
+ path
+ end
+
# @param [Base, String] other another code object (or object path)
# @return [String] the shortest relative path from this object to +other+
# @since 0.5.3
def relative_path(other)
other = Registry.at(other) if String === other && Registry.at(other)
@@ -507,10 +518,18 @@
# Tests if the {#docstring} has a tag
# @see Docstring#has_tag?
def has_tag?(name); docstring.has_tag?(name) end
+ # Add tags to the {#docstring}
+ # @see Docstring#add_tag
+ # @since 0.8.4
+ def add_tag(*tags)
+ @docstrings.clear
+ @base_docstring.add_tag(*tags)
+ end
+
# @return whether or not this object is a RootObject
def root?; false end
# Override this method with a custom component separator. For instance,
# {MethodObject} implements sep as '#' or '.' (depending on if the
@@ -530,11 +549,11 @@
# "@" prefix) that should be copied when {#copy_to} is called
# @see #copy_to
# @since 0.8.0
def copyable_attributes
vars = instance_variables.map {|ivar| ivar.to_s[1..-1] }
- vars -= %w(docstring namespace name path)
+ vars -= %w(base_docstring docstrings namespace name path)
vars
end
private
@@ -545,9 +564,20 @@
def format_source(source)
source.chomp!
last = source.split(/\r?\n/).last
indent = last ? last[/^([ \t]*)/, 1].length : 0
source.gsub(/^[ \t]{#{indent}}/, '')
+ end
+
+ def translate_docstring(locale)
+ @base_docstring.resolve_reference
+ return @base_docstring if locale.nil?
+
+ text = I18n::Text.new(@base_docstring)
+ localized_text = text.translate(locale)
+ docstring = Docstring.new(localized_text, self)
+ docstring.add_tag(*@base_docstring.tags)
+ docstring
end
end
end
end