# frozen_string_literal: true module LicenseFinder class Composer < PackageManager def prepare create_vendor_path within_project_path do tool_box.install(tool: :php) shell.execute([ :composer, :install, '--ignore-platform-reqs', '--no-dev', '--no-interaction', '--no-plugins', '--no-progress', '--no-scripts', '--verbose' ], env: default_env) end end def current_packages within_project_path do dependencies.map do |data| map_from(data) end end end private def default_env @default_env ||= { 'COMPOSER_ALLOW_SUPER' => '1', 'COMPOSER_CAFILE' => ENV.fetch('COMPOSER_CACHE_DIR', shell.default_certificate_path).to_s }.tap do |env| if vendor_path.exist? env['COMPOSER_CACHE_DIR'] = ENV.fetch('COMPOSER_CACHE_DIR', vendor_path.join('.cache')).to_s env['COMPOSER_VENDOR_DIR'] = ENV.fetch('COMPOSER_VENDOR_DIR', vendor_path).to_s end end end def dependencies stdout, _stderr, status = shell.execute([ :composer, :licenses, '--format=json' ], env: default_env) return from_lockfile unless status.success? dependencies = JSON.parse(stdout).fetch('dependencies', {}) return from_lockfile if dependencies.empty? dependencies.map do |name, data| data.merge('name' => name) if data.is_a?(Hash) end.compact end def map_from(data) Dependency.new( 'Composer', data['name'], data['version'], spec_licenses: data['license'], detection_path: detected_package_path, install_path: path_to(data['name']) ) end def path_to(package_name) stdout, _stderr, status = shell.execute([ :composer, :show, package_name, "-P" ], env: default_env) status.success? ? stdout.split(' ').last : '' end def from_lockfile return [] unless lockfile_path.exist? json = JSON.parse(lockfile_path.read) json.fetch('packages', []) end end end