bibliothecary 14.4.0 → 15.0.0

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.
Files changed (40) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +14 -0
  3. data/UPGRADING_TO_15_0_0.md +264 -0
  4. data/lib/bibliothecary/analyser/analysis.rb +2 -2
  5. data/lib/bibliothecary/analyser.rb +24 -20
  6. data/lib/bibliothecary/dependency.rb +1 -4
  7. data/lib/bibliothecary/file_info.rb +7 -3
  8. data/lib/bibliothecary/multi_parsers/cyclonedx.rb +24 -21
  9. data/lib/bibliothecary/multi_parsers/dependencies_csv.rb +7 -4
  10. data/lib/bibliothecary/multi_parsers/spdx.rb +40 -26
  11. data/lib/bibliothecary/{multi_parsers → parser_mixins}/bundler_like_manifest.rb +1 -1
  12. data/lib/bibliothecary/{multi_parsers → parser_mixins}/json_runtime.rb +1 -1
  13. data/lib/bibliothecary/parsers/bower.rb +0 -2
  14. data/lib/bibliothecary/parsers/cargo.rb +0 -4
  15. data/lib/bibliothecary/parsers/cocoapods.rb +1 -3
  16. data/lib/bibliothecary/parsers/conan.rb +0 -4
  17. data/lib/bibliothecary/parsers/conda.rb +0 -4
  18. data/lib/bibliothecary/parsers/cpan.rb +0 -2
  19. data/lib/bibliothecary/parsers/cran.rb +0 -4
  20. data/lib/bibliothecary/parsers/dub.rb +1 -3
  21. data/lib/bibliothecary/parsers/elm.rb +1 -3
  22. data/lib/bibliothecary/parsers/go.rb +0 -4
  23. data/lib/bibliothecary/parsers/haxelib.rb +1 -3
  24. data/lib/bibliothecary/parsers/julia.rb +0 -2
  25. data/lib/bibliothecary/parsers/maven.rb +0 -4
  26. data/lib/bibliothecary/parsers/meteor.rb +1 -3
  27. data/lib/bibliothecary/parsers/npm.rb +0 -4
  28. data/lib/bibliothecary/parsers/nuget.rb +1 -5
  29. data/lib/bibliothecary/parsers/packagist.rb +0 -4
  30. data/lib/bibliothecary/parsers/pub.rb +0 -2
  31. data/lib/bibliothecary/parsers/pypi.rb +0 -4
  32. data/lib/bibliothecary/parsers/rubygems.rb +1 -5
  33. data/lib/bibliothecary/parsers/shard.rb +0 -2
  34. data/lib/bibliothecary/parsers/vcpkg.rb +0 -4
  35. data/lib/bibliothecary/related_files_info.rb +19 -15
  36. data/lib/bibliothecary/runner/multi_manifest_filter.rb +2 -83
  37. data/lib/bibliothecary/runner.rb +40 -23
  38. data/lib/bibliothecary/version.rb +1 -1
  39. data/lib/bibliothecary.rb +16 -3
  40. metadata +5 -4
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d1f7fd4aeb8298f9fcb9b5edc69b7936eed8f112f3a6dde000edda36d641cfca
4
- data.tar.gz: 4d9b619aab4813b3ee77a36b0fbb1588b561a3dd42275feeb216f01d19f8ea05
3
+ metadata.gz: f0d3fafafd92ac4eac18f89f709733c655b0f05a803f9fcb2c1ef8b26690c584
4
+ data.tar.gz: b89c725a5bbbcc8139a8ebac579f610a84839e3eaaf356dd04fe4d371294ad03
5
5
  SHA512:
6
- metadata.gz: a9a904ac75104ea34f45bfea2900475c89fd29a5d15ac065923d4e9d4c715ec6380d92ecea6499025063abe8f0146d2a89d9661f59f98cd216a4dcc6ce44b054
7
- data.tar.gz: a4234dc007565e41587fa92ca7f970e5fdffd479debd202658e8a04edcf01943624df11aa1d0785398b87d10f694f3b84fb68fb985251315fbff67799f24fa2f
6
+ metadata.gz: 9b8caae9ff6a85ee12a1860f048e69c2910e7f48128a6621fc1c2d14ca587a79ca9478a14b5f092005edb02cc6ff00ee2819d6788a6a7f8fa95d5f10f1addf67
7
+ data.tar.gz: 408d3891213550d27395f65587010ee0c4a49da47fb290e3805971dbe7f41b7fe2add33c3d3c4dbe646e084b6536e4a33c15928e8560d32ffaa8fde45332b14b
data/CHANGELOG.md CHANGED
@@ -13,6 +13,20 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
13
13
 
14
14
  ### Removed
15
15
 
16
+ ## [15.0.0]
17
+
18
+ 15.0.0 includes some breaking changes, so please see UPGRADING_TO_15_0_0.md to migrate your code.
19
+
20
+ ### Changed
21
+
22
+ - Make the MultiParsers (CycloneDX, Spdx, DependenciesCSV) classes instead of modules.
23
+ - Moved the two parser mixins, JSONRuntime and BundlerLikeManifest, into their own Bibliothecary::ParserMixins namespace.
24
+ - Return all dependencies from SPDX and CycloneDX files regardless of platform
25
+
26
+ ### Removed
27
+
28
+ - Removed MultiManifestFilter, since it's no longer necessary
29
+
16
30
  ## [14.4.0]
17
31
 
18
32
  ### Added
@@ -0,0 +1,264 @@
1
+ # Upgrading to Bibliothecary 15.0.0
2
+
3
+ Bibliothecary 15.0.0 includes several breaking changes related to how parsers are structured and how analysis results are returned. This guide will help you upgrade your code.
4
+
5
+ ## Breaking Changes
6
+
7
+ ### 1. Analysis Results Now Use `parser` Instead of `platform`
8
+
9
+ **What Changed:**
10
+ - Analysis result hashes now use the key `parser:` instead of `platform:`
11
+ - `Bibliothecary::Analyser.create_analysis()` returns `parser:` instead of `platform:`
12
+ - `Bibliothecary::Analyser.create_error_analysis()` returns `parser:` instead of `platform:`
13
+
14
+ **Before (14.x):**
15
+ ```ruby
16
+ analysis = Bibliothecary.analyse('path/to/project')
17
+ # => [{
18
+ # platform: "npm",
19
+ # path: "package.json",
20
+ # dependencies: [...],
21
+ # kind: "manifest",
22
+ # success: true
23
+ # }]
24
+
25
+ analysis.first[:platform] # => "npm"
26
+ ```
27
+
28
+ **After (15.0):**
29
+ ```ruby
30
+ analysis = Bibliothecary.analyse('path/to/project')
31
+ # => [{
32
+ # parser: "npm",
33
+ # path: "package.json",
34
+ # dependencies: [...],
35
+ # kind: "manifest",
36
+ # success: true
37
+ # }]
38
+
39
+ analysis.first[:parser] # => "npm"
40
+ ```
41
+
42
+ **Migration:**
43
+ - Replace all references to `analysis[:platform]` with `analysis[:parser]`
44
+ - Update any code that expects the `platform` key in analysis results
45
+ - Note: `Dependency` objects still use `platform:` as this refers to the ecosystem, not the parser
46
+
47
+ ### 2. SBOM Files Now Return Single Parser Results
48
+
49
+ **What Changed:**
50
+ - SBOM files (CycloneDX, SPDX, dependencies.csv) are now parsed as standalone parser results
51
+ - Previously, multi-parsers would distribute dependencies across multiple platform-specific results
52
+ - Now, all dependencies from an SBOM file are returned in a single result with the SBOM parser name
53
+
54
+ **Before (14.x):**
55
+ ```ruby
56
+ # A cyclonedx.json file containing npm and maven dependencies would return:
57
+ [
58
+ {
59
+ platform: "npm",
60
+ path: "cyclonedx.json",
61
+ dependencies: [<npm deps>],
62
+ ...
63
+ },
64
+ {
65
+ platform: "maven",
66
+ path: "cyclonedx.json",
67
+ dependencies: [<maven deps>],
68
+ ...
69
+ }
70
+ ]
71
+ ```
72
+
73
+ **After (15.0):**
74
+ ```ruby
75
+ # The same cyclonedx.json file now returns a single result:
76
+ [
77
+ {
78
+ parser: "cyclonedx",
79
+ path: "cyclonedx.json",
80
+ dependencies: [<all deps with their platform: field set>],
81
+ kind: "lockfile",
82
+ success: true
83
+ }
84
+ ]
85
+
86
+ # Each dependency still knows its platform:
87
+ dependencies.first.platform # => "npm"
88
+ dependencies.last.platform # => "maven"
89
+ ```
90
+
91
+ **Migration:**
92
+ - Update code that expects SBOM files to return multiple platform-specific results
93
+ - Instead of filtering results by `platform`, check `result[:parser]` for "cyclonedx", "spdx", or "dependenciescsv"
94
+ - Group dependencies by their `Dependency#platform` field if you need platform-specific grouping
95
+
96
+ **Affected Parsers:**
97
+ - `cyclonedx` (cyclonedx.json, cyclonedx.xml, *.cdx.json, *.cdx.xml)
98
+ - `spdx` (*.spdx, *.spdx.json)
99
+ - `dependenciescsv` (dependencies.csv)
100
+
101
+ ### 3. SBOM Files Now Return ALL Dependencies Regardless of Platform
102
+
103
+ **What Changed:**
104
+ - CycloneDX and SPDX parsers now return ALL dependencies from SBOM files
105
+ - Previously, only dependencies with PURL types mapped in `PURL_TYPE_MAPPING` were returned
106
+ - Now, unmapped PURL types (e.g., `alpine`, `apk`, `deb`, `rpm`) are included with the PURL type used as the platform name
107
+
108
+ **Before (14.x):**
109
+ ```ruby
110
+ # An SBOM with npm, maven, and alpine packages would only return npm and maven
111
+ result = Bibliothecary.analyse('cyclonedx.json')
112
+ # => [{
113
+ # parser: "cyclonedx",
114
+ # dependencies: [
115
+ # { name: "express", platform: "npm", ... }, # included
116
+ # { name: "junit", platform: "maven", ... }, # included
117
+ # # alpine packages were silently filtered out
118
+ # ]
119
+ # }]
120
+ ```
121
+
122
+ **After (15.0):**
123
+ ```ruby
124
+ # The same SBOM now returns ALL packages
125
+ result = Bibliothecary.analyse('cyclonedx.json')
126
+ # => [{
127
+ # parser: "cyclonedx",
128
+ # dependencies: [
129
+ # { name: "express", platform: "npm", ... }, # included (mapped)
130
+ # { name: "junit", platform: "maven", ... }, # included (mapped)
131
+ # { name: "alpine-base", platform: "alpine", ... }, # included (unmapped, uses PURL type)
132
+ # { name: "curl", platform: "apk", ... } # included (unmapped, uses PURL type)
133
+ # ]
134
+ # }]
135
+ ```
136
+
137
+ **Mapped PURL Types (in PURL_TYPE_MAPPING):**
138
+ - `golang` → `go`
139
+ - `maven` → `maven`
140
+ - `npm` → `npm`
141
+ - `cargo` → `cargo`
142
+ - `composer` → `packagist`
143
+ - `conan` → `conan`
144
+ - `conda` → `conda`
145
+ - `cran` → `cran`
146
+ - `gem` → `rubygems`
147
+ - `nuget` → `nuget`
148
+ - `pypi` → `pypi`
149
+ - `vcpkg` → `vcpkg`
150
+
151
+ **Unmapped PURL Types (now included as-is):**
152
+ - `alpine`, `apk`, `deb`, `rpm`, `bitbucket`, `github`, `docker`, and any other PURL types
153
+
154
+ **Migration:**
155
+ - If your code filters or groups by platform, be aware that new platform values may appear
156
+ - System package types (`alpine`, `apk`, `deb`, `rpm`) will now be included in results
157
+ - Consider whether your application needs to handle these additional platform types
158
+ - The behavior is now more comprehensive and accurate to what's actually in SBOM files
159
+
160
+ ### 4. API Method Renames
161
+
162
+ **What Changed:**
163
+ - Methods containing "package_manager" have been renamed to "parser"
164
+ - Old methods now raise errors with upgrade instructions
165
+
166
+ **Removed Methods:**
167
+
168
+ | Old Method (14.x) | New Method (15.0) |
169
+ |-------------------|-------------------|
170
+ | `Bibliothecary.package_managers` | `Bibliothecary.parsers` |
171
+ | `Bibliothecary.applicable_package_managers(info)` | `Bibliothecary.applicable_parsers(info)` |
172
+ | `Runner#package_managers` | `Runner#parsers` |
173
+ | `Runner#applicable_package_managers(info)` | `Runner#applicable_parsers(info)` |
174
+ | `FileInfo#package_manager` | `FileInfo#parser` |
175
+ | `RelatedFilesInfo#package_manager` | `RelatedFilesInfo#parser` |
176
+
177
+ **Before (14.x):**
178
+ ```ruby
179
+ Bibliothecary.package_managers
180
+ # => [Bibliothecary::Parsers::NPM, Bibliothecary::Parsers::Rubygems, ...]
181
+
182
+ info = Bibliothecary::FileInfo.new(...)
183
+ parsers = Bibliothecary.applicable_package_managers(info)
184
+ ```
185
+
186
+ **After (15.0):**
187
+ ```ruby
188
+ Bibliothecary.parsers
189
+ # => [Bibliothecary::Parsers::NPM, Bibliothecary::MultiParsers::CycloneDX, ...]
190
+
191
+ info = Bibliothecary::FileInfo.new(...)
192
+ parsers = Bibliothecary.applicable_parsers(info)
193
+ ```
194
+
195
+ **Migration:**
196
+ - Search and replace `package_managers` with `parsers` in your codebase
197
+ - Search and replace `applicable_package_managers` with `applicable_parsers`
198
+ - Update any references to `FileInfo#package_manager` to use `FileInfo#parser`
199
+
200
+ ### 4. MultiManifestFilter Removed
201
+
202
+ **What Changed:**
203
+ - The `Bibliothecary::Runner::MultiManifestFilter` class has been removed
204
+ - Multi-parsers are now standalone parser classes and don't require special filtering
205
+
206
+ **Before (14.x):**
207
+ ```ruby
208
+ # MultiManifestFilter was used internally to handle SBOM files
209
+ ```
210
+
211
+ **After (15.0):**
212
+ ```ruby
213
+ # Multi-parsers (CycloneDX, SPDX, DependenciesCSV) are regular parser classes
214
+ # They are included automatically in Bibliothecary.parsers
215
+ ```
216
+
217
+ **Migration:**
218
+ - Remove any direct references to `Bibliothecary::Runner::MultiManifestFilter`
219
+ - The new behavior handles SBOM files transparently through the regular parser system
220
+
221
+ ### 5. Parser Mixins Moved
222
+
223
+ **What Changed:**
224
+ - `Bibliothecary::MultiParsers::JSONRuntime` moved to `Bibliothecary::ParserMixins::JSONRuntime`
225
+ - `Bibliothecary::MultiParsers::BundlerLikeManifest` moved to `Bibliothecary::ParserMixins::BundlerLikeManifest`
226
+
227
+ **Migration:**
228
+ - Update any explicit references to these modules in your code
229
+ - Most users won't be affected as these are internal implementation details
230
+
231
+ ### 6. MultiParsers Are Now Classes
232
+
233
+ **What Changed:**
234
+ - Multi-parsers (CycloneDX, SPDX, DependenciesCSV) are now classes instead of modules
235
+ - They are no longer mixed into platform-specific parsers
236
+ - They are standalone parsers included in `Bibliothecary.parsers`
237
+
238
+ **Before (14.x):**
239
+ ```ruby
240
+ # Multi-parsers were modules that extended individual parsers
241
+ Bibliothecary::Parsers::NPM.ancestors
242
+ # => includes Bibliothecary::MultiParsers::CycloneDX
243
+ ```
244
+
245
+ **After (15.0):**
246
+ ```ruby
247
+ # Multi-parsers are independent parser classes
248
+ Bibliothecary.parsers
249
+ # => [
250
+ # Bibliothecary::Parsers::NPM,
251
+ # Bibliothecary::Parsers::Maven,
252
+ # ...,
253
+ # Bibliothecary::MultiParsers::CycloneDX,
254
+ # Bibliothecary::MultiParsers::Spdx,
255
+ # Bibliothecary::MultiParsers::DependenciesCSV
256
+ # ]
257
+
258
+ # They have their own platform_name
259
+ Bibliothecary::MultiParsers::CycloneDX.platform_name # => "cyclonedx"
260
+ ```
261
+
262
+ **Migration:**
263
+ - Don't rely on multi-parser methods being available on platform-specific parsers
264
+ - Treat SBOM parsers as independent parsers in your code
@@ -43,9 +43,9 @@ module Bibliothecary
43
43
  parser_result = parse_file(info.relative_path, info.contents, options: options)
44
44
  parser_result = ParserResult.new(dependencies: []) if parser_result.nil? # work around any legacy parsers that return nil
45
45
 
46
- Bibliothecary::Analyser.create_analysis(platform_name, info.relative_path, kind, parser_result)
46
+ Bibliothecary::Analyser.create_analysis(parser_name, info.relative_path, kind, parser_result)
47
47
  rescue Bibliothecary::FileParsingError => e
48
- Bibliothecary::Analyser.create_error_analysis(platform_name, info.relative_path, kind, e.message, e.location)
48
+ Bibliothecary::Analyser.create_error_analysis(parser_name, info.relative_path, kind, e.message, e.location)
49
49
  end
50
50
  alias analyze_contents_from_info analyse_contents_from_info
51
51
 
@@ -6,9 +6,9 @@ require_relative "analyser/analysis"
6
6
 
7
7
  module Bibliothecary
8
8
  module Analyser
9
- def self.create_error_analysis(platform_name, relative_path, kind, message, location = nil)
9
+ def self.create_error_analysis(parser_name, relative_path, kind, message, location = nil)
10
10
  {
11
- platform: platform_name,
11
+ parser: parser_name,
12
12
  path: relative_path,
13
13
  dependencies: nil,
14
14
  kind: kind,
@@ -18,9 +18,9 @@ module Bibliothecary
18
18
  }
19
19
  end
20
20
 
21
- def self.create_analysis(platform_name, relative_path, kind, parser_result)
21
+ def self.create_analysis(parser_name, relative_path, kind, parser_result)
22
22
  {
23
- platform: platform_name,
23
+ parser: parser_name,
24
24
  path: relative_path,
25
25
  project_name: parser_result.project_name,
26
26
  dependencies: parser_result.dependencies,
@@ -52,13 +52,17 @@ module Bibliothecary
52
52
 
53
53
  module ClassMethods
54
54
  def platform_name
55
- @platform_name ||= name.to_s.split("::").last.downcase.freeze
55
+ parser_name
56
+ end
57
+
58
+ def parser_name
59
+ @parser_name ||= name.to_s.split("::").last.downcase.freeze
56
60
  end
57
61
 
58
62
  def map_dependencies(hash, key, type, source = nil)
59
63
  hash.fetch(key, []).map do |name, requirement|
60
64
  Dependency.new(
61
- platform: platform_name,
65
+ platform: parser_name,
62
66
  name: name,
63
67
  requirement: requirement,
64
68
  type: type,
@@ -67,23 +71,23 @@ module Bibliothecary
67
71
  end
68
72
  end
69
73
 
70
- # Add a MultiParser module to a Parser class. This extends the
71
- # self.mapping method on the parser to include the multi parser's
72
- # files to watch for, and it extends the Parser class with
73
- # the multi parser for you.
74
- #
75
- # @param klass [Class] A Bibliothecary::MultiParsers class
76
- def add_multi_parser(klass)
77
- raise "No mapping found! You should place the add_multi_parser call below def self.mapping." unless respond_to?(:mapping)
74
+ # # Add a MultiParser module to a Parser class. This extends the
75
+ # # self.mapping method on the parser to include the multi parser's
76
+ # # files to watch for, and it extends the Parser class with
77
+ # # the multi parser for you.
78
+ # #
79
+ # # @param klass [Class] A Bibliothecary::MultiParsers class
80
+ # def add_multi_parser(klass)
81
+ # raise "No mapping found! You should place the add_multi_parser call below def self.mapping." unless respond_to?(:mapping)
78
82
 
79
- original_mapping = mapping
83
+ # original_mapping = mapping
80
84
 
81
- define_singleton_method(:mapping) do
82
- original_mapping.merge(klass.mapping)
83
- end
85
+ # define_singleton_method(:mapping) do
86
+ # original_mapping.merge(klass.mapping)
87
+ # end
84
88
 
85
- send(:extend, klass)
86
- end
89
+ # send(:extend, klass)
90
+ # end
87
91
  end
88
92
  end
89
93
  end
@@ -5,10 +5,7 @@ module Bibliothecary
5
5
  #
6
6
  # @attr_reader [String] name The name of the package, e.g. "ansi-string-colors"
7
7
  # @attr_reader [String] requirement The version requirement of the release, e.g. "1.0.0" or "^1.0.0"
8
- # @attr_reader [String] platform The platform of the package, e.g. "maven". This is optional because
9
- # it's implicit in most parser results, and the analyzer returns the platform name itself. One
10
- # exception are multi-parsers like DependenciesCSV, because they may return deps from multiple platforms.
11
- # Bibliothecary could start returning this field for *all* deps in future, and make it required. (default: nil)
8
+ # @attr_reader [String] platform The platform of the package, e.g. "maven".
12
9
  # @attr_reader [String] type The type or scope of dependency, e.g. "runtime" or "test". In some ecosystems a
13
10
  # default may be set and in other ecosystems it may make sense to return nil when not found.
14
11
  # @attr_reader [Boolean] direct Is this dependency a direct dependency (vs transitive dependency)? (default: nil)
@@ -7,7 +7,11 @@ module Bibliothecary
7
7
  # and package manager information if needed.
8
8
  class FileInfo
9
9
  attr_reader :folder_path, :relative_path, :full_path
10
- attr_accessor :package_manager
10
+ attr_accessor :parser
11
+
12
+ def package_manager
13
+ raise "FileInfo#package_manager() has been removed in bibliothecary 15.0.0. Use parser() instead, which now includes MultiParsers."
14
+ end
11
15
 
12
16
  def contents
13
17
  @contents ||=
@@ -45,11 +49,11 @@ module Bibliothecary
45
49
 
46
50
  @contents = contents
47
51
 
48
- @package_manager = nil
52
+ @parser = nil
49
53
  end
50
54
 
51
55
  def groupable?
52
- @package_manager&.groupable?(self)
56
+ @parser&.groupable?(self)
53
57
  end
54
58
  end
55
59
  end
@@ -12,17 +12,17 @@ Warning[:experimental] = true
12
12
 
13
13
  module Bibliothecary
14
14
  module MultiParsers
15
- module CycloneDX
15
+ class CycloneDX
16
16
  include Bibliothecary::Analyser
17
- include Bibliothecary::Analyser::TryCache
17
+ extend Bibliothecary::Analyser::TryCache
18
18
 
19
19
  NoComponents = Class.new(StandardError)
20
20
 
21
21
  class ManifestEntries
22
- attr_reader :manifests
22
+ attr_reader :entries
23
23
 
24
24
  def initialize(parse_queue:)
25
- @manifests = {}
25
+ @entries = Set.new
26
26
 
27
27
  # Instead of recursing, we'll work through a queue of components
28
28
  # to process, letting the different parser add components to the
@@ -31,14 +31,13 @@ module Bibliothecary
31
31
  end
32
32
 
33
33
  def add(purl, source = nil)
34
- mapping = PurlUtil::PURL_TYPE_MAPPING[purl.type]
35
- return unless mapping
34
+ # Use the mapped purl->bibliothecary platform, or else fall back to original platform itself.
35
+ mapping = PurlUtil::PURL_TYPE_MAPPING.fetch(purl.type, purl.type)
36
36
 
37
- @manifests[mapping] ||= Set.new
38
- @manifests[mapping] << Dependency.new(
37
+ @entries << Dependency.new(
39
38
  name: PurlUtil.full_name(purl),
40
39
  requirement: purl.version,
41
- platform: mapping.to_s,
40
+ platform: mapping ? mapping.to_s : purl.type,
42
41
  type: "lockfile",
43
42
  source: source
44
43
  )
@@ -60,10 +59,6 @@ module Bibliothecary
60
59
  add(purl, source)
61
60
  end
62
61
  end
63
-
64
- def [](key)
65
- @manifests[key]&.to_a
66
- end
67
62
  end
68
63
 
69
64
  def self.mapping
@@ -91,25 +86,31 @@ module Bibliothecary
91
86
  }
92
87
  end
93
88
 
94
- def parse_cyclonedx_json(file_contents, options: {})
89
+ def self.platform_name
90
+ raise "CycloneDX is a multi-parser and does not have a platform name."
91
+ end
92
+
93
+ def self.parse_cyclonedx_json(file_contents, options: {})
95
94
  manifest = try_cache(options, options[:filename]) do
96
95
  JSON.parse(file_contents)
97
96
  end
98
97
 
99
98
  raise NoComponents unless manifest["components"]
100
99
 
101
- entries = ManifestEntries.new(parse_queue: manifest["components"])
100
+ manifest_entries = ManifestEntries.new(
101
+ parse_queue: manifest["components"]
102
+ )
102
103
 
103
- entries.parse!(options.fetch(:filename, nil)) do |component, parse_queue|
104
+ manifest_entries.parse!(options.fetch(:filename, nil)) do |component, parse_queue|
104
105
  parse_queue.concat(component["components"]) if component["components"]
105
106
 
106
107
  component["purl"]
107
108
  end
108
109
 
109
- ParserResult.new(dependencies: entries[platform_name.to_sym] || [])
110
+ ParserResult.new(dependencies: manifest_entries.entries.to_a)
110
111
  end
111
112
 
112
- def parse_cyclonedx_xml(file_contents, options: {})
113
+ def self.parse_cyclonedx_xml(file_contents, options: {})
113
114
  manifest = try_cache(options, options[:filename]) do
114
115
  Ox.parse(file_contents)
115
116
  end
@@ -121,9 +122,11 @@ module Bibliothecary
121
122
 
122
123
  raise NoComponents unless root.locate("components").first
123
124
 
124
- entries = ManifestEntries.new(parse_queue: root.locate("components/*"))
125
+ manifest_entries = ManifestEntries.new(
126
+ parse_queue: root.locate("components/*")
127
+ )
125
128
 
126
- entries.parse!(options.fetch(:filename, nil)) do |component, parse_queue|
129
+ manifest_entries.parse!(options.fetch(:filename, nil)) do |component, parse_queue|
127
130
  # #locate returns an empty array if nothing is found, so we can
128
131
  # always safely concatenate it to the parse queue.
129
132
  parse_queue.concat(component.locate("components/*"))
@@ -131,7 +134,7 @@ module Bibliothecary
131
134
  component.locate("purl").first&.text
132
135
  end
133
136
 
134
- ParserResult.new(dependencies: entries[platform_name.to_sym] || [])
137
+ ParserResult.new(dependencies: manifest_entries.entries.to_a)
135
138
  end
136
139
  end
137
140
  end
@@ -4,9 +4,9 @@ require "csv"
4
4
 
5
5
  module Bibliothecary
6
6
  module MultiParsers
7
- module DependenciesCSV
7
+ class DependenciesCSV
8
8
  include Bibliothecary::Analyser
9
- include Bibliothecary::Analyser::TryCache
9
+ extend Bibliothecary::Analyser::TryCache
10
10
 
11
11
  def self.mapping
12
12
  {
@@ -18,6 +18,10 @@ module Bibliothecary
18
18
  }
19
19
  end
20
20
 
21
+ def self.platform_name
22
+ raise "DependenciesCSV is a multi-parser and does not have a platform name."
23
+ end
24
+
21
25
  # Processing a CSV file isn't as exact as using a real manifest file,
22
26
  # but you can get pretty close as long as the data you're importing
23
27
  # is simple.
@@ -132,7 +136,7 @@ module Bibliothecary
132
136
  end
133
137
  end
134
138
 
135
- def parse_dependencies_csv(file_contents, options: {})
139
+ def self.parse_dependencies_csv(file_contents, options: {})
136
140
  csv_file = try_cache(options, options[:filename]) do
137
141
  raw_csv_file = CSVFile.new(file_contents)
138
142
  raw_csv_file.parse!
@@ -141,7 +145,6 @@ module Bibliothecary
141
145
 
142
146
  dependencies = csv_file
143
147
  .result
144
- .find_all { |dependency| dependency[:platform] == platform_name.to_s }
145
148
  .map do |dep_kvs|
146
149
  Dependency.new(
147
150
  **dep_kvs, source: options.fetch(:filename, nil)