Module: Bibliothecary::Analyser::ClassMethods
- Defined in:
- lib/bibliothecary/analyser.rb
Instance Method Summary collapse
- #analyse(folder_path, file_list) ⇒ Object
- #analyse_contents(filename, contents) ⇒ Object
- #analyse_contents_from_info(info) ⇒ Object
- #analyse_file_info(file_info_list) ⇒ Object
-
#determine_can_have_lockfile(filename, contents = nil) ⇒ Object
calling this with contents=nil can produce less-informed results, but kept for back compat.
- #determine_can_have_lockfile_from_info(info) ⇒ Object
-
#determine_kind(filename, contents = nil) ⇒ Object
calling this with contents=nil can produce less-informed results, but kept for back compat.
- #determine_kind_from_info(info) ⇒ Object
- #map_dependencies(hash, key, type) ⇒ Object
- #mapping_entry_match?(matcher, details, info) ⇒ Boolean
-
#match?(filename, contents = nil) ⇒ Boolean
this is broken with contents=nil because it can’t look at file contents, so skips manifests that are ambiguously a manifest considering only the filename.
- #match_extension(filename, case_insensitive: false) ⇒ Object
- #match_filename(filename, case_insensitive: false) ⇒ Object
- #match_filenames(*filenames) ⇒ Object
- #match_info?(info) ⇒ Boolean
- #parse_file(filename, contents) ⇒ Object
- #parse_json_runtime_manifest(file_contents) ⇒ Object
- #parse_ruby_manifest(manifest) ⇒ Object
- #platform_name ⇒ Object
Instance Method Details
#analyse(folder_path, file_list) ⇒ Object
101 102 103 |
# File 'lib/bibliothecary/analyser.rb', line 101 def analyse(folder_path, file_list) analyse_file_info(file_list.map { |full_path| FileInfo.new(folder_path, full_path) }) end |
#analyse_contents(filename, contents) ⇒ Object
115 116 117 |
# File 'lib/bibliothecary/analyser.rb', line 115 def analyse_contents(filename, contents) analyse_contents_from_info(FileInfo.new(nil, filename, contents)) end |
#analyse_contents_from_info(info) ⇒ Object
119 120 121 122 123 124 125 126 127 128 |
# File 'lib/bibliothecary/analyser.rb', line 119 def analyse_contents_from_info(info) # If your Parser needs to return multiple responses for one file, please override this method # For example see conda.rb kind = determine_kind_from_info(info) dependencies = parse_file(info.relative_path, info.contents) Bibliothecary::Analyser::create_analysis(platform_name, info.relative_path, kind, dependencies || []) rescue Bibliothecary::FileParsingError => e Bibliothecary::Analyser::create_error_analysis(platform_name, info.relative_path, kind, e.) end |
#analyse_file_info(file_info_list) ⇒ Object
105 106 107 108 109 110 111 112 113 |
# File 'lib/bibliothecary/analyser.rb', line 105 def analyse_file_info(file_info_list) matching_info = file_info_list .select(&method(:match_info?)) matching_info.flat_map do |info| analyse_contents_from_info(info) .merge(related_paths: (info, matching_info)) end end |
#determine_can_have_lockfile(filename, contents = nil) ⇒ Object
calling this with contents=nil can produce less-informed results, but kept for back compat
143 144 145 |
# File 'lib/bibliothecary/analyser.rb', line 143 def determine_can_have_lockfile(filename, contents = nil) determine_can_have_lockfile_from_info(FileInfo.new(nil, filename, contents)) end |
#determine_can_have_lockfile_from_info(info) ⇒ Object
147 148 149 150 |
# File 'lib/bibliothecary/analyser.rb', line 147 def determine_can_have_lockfile_from_info(info) first_matching_mapping_details(info) .fetch(:can_have_lockfile, true) end |
#determine_kind(filename, contents = nil) ⇒ Object
calling this with contents=nil can produce less-informed results, but kept for back compat
132 133 134 |
# File 'lib/bibliothecary/analyser.rb', line 132 def determine_kind(filename, contents = nil) determine_kind_from_info(FileInfo.new(nil, filename, contents)) end |
#determine_kind_from_info(info) ⇒ Object
136 137 138 139 |
# File 'lib/bibliothecary/analyser.rb', line 136 def determine_kind_from_info(info) first_matching_mapping_details(info) .fetch(:kind, nil) end |
#map_dependencies(hash, key, type) ⇒ Object
91 92 93 94 95 96 97 98 99 |
# File 'lib/bibliothecary/analyser.rb', line 91 def map_dependencies(hash, key, type) hash.fetch(key,[]).map do |name, requirement| { name: name, requirement: requirement, type: type } end end |
#mapping_entry_match?(matcher, details, info) ⇒ Boolean
28 29 30 31 32 33 34 35 36 37 38 39 40 41 |
# File 'lib/bibliothecary/analyser.rb', line 28 def mapping_entry_match?(matcher, details, info) if matcher.call(info.relative_path) # we only want to load contents if we don't have them already # and there's a content_matcher method to use return true if details[:content_matcher].nil? # this is the libraries.io case where we won't load all .xml # files (for example) just to look at their contents, we'll # assume they are not manifests. return false if info.contents.nil? return send(details[:content_matcher], info.contents) else return false end end |
#match?(filename, contents = nil) ⇒ Boolean
this is broken with contents=nil because it can’t look at file contents, so skips manifests that are ambiguously a manifest considering only the filename. However, those are the semantics that libraries.io uses since it doesn’t have the files locally.
69 70 71 |
# File 'lib/bibliothecary/analyser.rb', line 69 def match?(filename, contents = nil) match_info?(FileInfo.new(nil, filename, contents)) end |
#match_extension(filename, case_insensitive: false) ⇒ Object
182 183 184 185 186 187 188 |
# File 'lib/bibliothecary/analyser.rb', line 182 def match_extension(filename, case_insensitive: false) if case_insensitive lambda { |path| path.downcase.end_with?(filename.downcase) } else lambda { |path| path.end_with?(filename) } end end |
#match_filename(filename, case_insensitive: false) ⇒ Object
167 168 169 170 171 172 173 |
# File 'lib/bibliothecary/analyser.rb', line 167 def match_filename(filename, case_insensitive: false) if case_insensitive lambda { |path| path.downcase == filename.downcase || path.downcase.end_with?("/" + filename.downcase) } else lambda { |path| path == filename || path.end_with?("/" + filename) } end end |
#match_filenames(*filenames) ⇒ Object
175 176 177 178 179 180 |
# File 'lib/bibliothecary/analyser.rb', line 175 def match_filenames(*filenames) lambda do |path| filenames.any? { |f| path == f } || filenames.any? { |f| path.end_with?("/" + f) } end end |
#match_info?(info) ⇒ Boolean
73 74 75 |
# File 'lib/bibliothecary/analyser.rb', line 73 def match_info?(info) first_matching_mapping_details(info).any? end |
#parse_file(filename, contents) ⇒ Object
43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
# File 'lib/bibliothecary/analyser.rb', line 43 def parse_file(filename, contents) details = first_matching_mapping_details(FileInfo.new(nil, filename, contents)) # this can be raised if we don't check match?/match_info?, # OR don't have the file contents when we check them, so # it turns out for example that a .xml file isn't a # manifest after all. raise Bibliothecary::FileParsingError.new("No parser for this file type", filename) unless details[:parser] # The `parser` method should raise an exception if the file is malformed, # should return empty [] if the file is fine but simply doesn't contain # any dependencies, and should never return nil. At the time of writing # this comment, some of the parsers return [] or nil to mean an error # which is confusing to users. send(details[:parser], contents) rescue Exception => e # default is StandardError but C bindings throw Exceptions # the C xml parser also puts a newline at the end of the message raise Bibliothecary::FileParsingError.new(e..strip, filename) end |
#parse_json_runtime_manifest(file_contents) ⇒ Object
81 82 83 84 85 86 87 88 89 |
# File 'lib/bibliothecary/analyser.rb', line 81 def parse_json_runtime_manifest(file_contents) JSON.parse(file_contents).fetch('dependencies',[]).map do |name, requirement| { name: name, requirement: requirement, type: 'runtime' } end end |
#parse_ruby_manifest(manifest) ⇒ Object
152 153 154 155 156 157 158 159 160 161 162 163 164 165 |
# File 'lib/bibliothecary/analyser.rb', line 152 def parse_ruby_manifest(manifest) manifest.dependencies.inject([]) do |deps, dep| deps.push({ name: dep.name, requirement: dep .requirement .requirements .sort_by(&:last) .map { |op, version| "#{op} #{version}" } .join(", "), type: dep.type }) end.uniq end |
#platform_name ⇒ Object
77 78 79 |
# File 'lib/bibliothecary/analyser.rb', line 77 def platform_name self.name.to_s.split('::').last.downcase end |