实现了 Rails::Command::NotesCommand 背后的逻辑。有关用法信息,请参阅 rails notes --help。
Annotation 对象是三元组 :line、:tag、:text,它们代表注解所在的行、其标签和其文本。请注意,文件名不会被存储。
注解在注释中被查找,并忽略空格,它们必须以标签开头,后面可以选择性地跟着一个冒号。行尾(或闭合的 ERB 注释标签)之前的所有内容都被认为是它们的文本。
- 类 Rails::SourceAnnotationExtractor::Annotation
- 类 Rails::SourceAnnotationExtractor::ParserExtractor
- 类 Rails::SourceAnnotationExtractor::PatternExtractor
Attributes
| [R] | tag |
类公共方法
enumerate(tag = nil, options = {}) 链接
打印在根目录 app、config、db、lib 和 test(递归)下的所有带有 tag 标签的注解。
如果 tag 为 nil,则打印带有默认或已注册标签的注解。
可以使用 options 中的 :dirs 键明确指定特定目录。
Rails::SourceAnnotationExtractor.enumerate 'TODO|FIXME', dirs: %w(app lib), tag: true
如果 options 有一个 :tag 标志,它将被传递给每个注解的 to_s。
有关将被考虑的文件扩展名列表,请参阅 SourceAnnotationExtractor#find_in。
这个类方法是 rails notes 命令的唯一入口点。
来源: 显示 | 在 GitHub 上
# File railties/lib/rails/source_annotation_extractor.rb, line 145 def self.enumerate(tag = nil, options = {}) tag ||= Annotation.tags.join("|") extractor = new(tag) dirs = options.delete(:dirs) || Annotation.directories extractor.display(extractor.find(dirs), options) end
new(tag) 链接
来源: 显示 | 在 GitHub 上
# File railties/lib/rails/source_annotation_extractor.rb, line 154 def initialize(tag) @tag = tag end
实例公共方法
display(results, options = {}) 链接
按文件名排序,打印 results 中文件名到注解的映射。options 哈希会被传递给每个注解的 to_s。
来源: 显示 | 在 GitHub 上
# File railties/lib/rails/source_annotation_extractor.rb, line 203 def display(results, options = {}) options[:indent] = results.flat_map { |f, a| a.map(&:line) }.max.to_s.size results.keys.sort.each do |file| puts "#{file}:" results[file].each do |note| puts " * #{note.to_s(options)}" end puts end end
find(dirs) 链接
返回一个哈希,将 dirs(递归)下的文件名映射到包含其注解的数组。
来源: 显示 | 在 GitHub 上
# File railties/lib/rails/source_annotation_extractor.rb, line 160 def find(dirs) dirs.inject({}) { |h, dir| h.update(find_in(dir)) } end
find_in(dir) 链接
返回一个哈希,将 dir(递归)下的文件名映射到包含其注解的数组。在 Rails::SourceAnnotationExtractor::Annotation.extensions 中注册了扩展名的文件将被考虑在内。只包括带有注解的文件。
来源: 显示 | 在 GitHub 上
# File railties/lib/rails/source_annotation_extractor.rb, line 168 def find_in(dir) results = {} Dir.glob("#{dir}/*") do |item| next if File.basename(item).start_with?(".") if File.directory?(item) results.update(find_in(item)) else extension = Annotation.extensions.detect do |regexp, _block| regexp.match(item) end if extension pattern = extension.last.call(tag) # In case a user-defined pattern returns nothing for the given set # of tags, we exit early. next unless pattern # If a user-defined pattern returns a regular expression, we will # wrap it in a PatternExtractor to keep the same API. pattern = PatternExtractor.new(pattern) if pattern.is_a?(Regexp) annotations = pattern.annotations(item) results.update(item => annotations) if annotations.any? end end end results end