#!/usr/bin/env ruby require 'sord' require 'commander/import' require 'bundler' program :name, 'sord' program :version, Sord::VERSION program :description, 'Generate Sorbet RBIs from YARD documentation' default_command :gen command :gen do |c| c.syntax = 'sord gen [options]' c.description = 'Generates a type signature file from this directory\'s YARD docs' c.option '--rbi', 'Use Sorbet\'s RBI format' c.option '--rbs', 'Use Steep/Ruby 3\'s RBS format' c.option '--[no-]sord-comments', 'Controls informational/warning comments in the file' c.option '--[no-]regenerate', 'Controls whether YARD is executed before Sord runs' c.option '--break-params INTEGER', Integer, 'Break params onto their own lines if there are this many' c.option '--replace-errors-with-untyped', 'Uses T.untyped rather than SORD_ERROR_ constants' c.option '--replace-unresolved-with-untyped', 'Uses T.untyped when Sord is unable to resolve a constant' c.option '--exclude-messages STRING', String, 'Blacklists a comma-separated string of log message types' c.option '--include-messages STRING', String, 'Whitelists a comma-separated string of log message types' c.option '--keep-original-comments', 'Retains original YARD comments rather than converting them to Markdown' c.option '--skip-constants', 'Excludes constants from generated file' c.option '--use-original-initialize-return', 'Uses the specified return type for #initialize rather than void' c.option '--exclude-untyped', 'Exclude methods and attributes with untyped return values' c.action do |args, options| options.default( rbi: false, rbs: false, sord_comments: true, regenerate: true, break_params: 4, replace_errors_with_untyped: false, replace_unresolved_with_untyped: false, exclude_messages: nil, include_messages: nil, keep_original_comments: false, skip_constants: false, use_original_initialize_return: false, exclude_untyped: false, ) if args.length != 1 Sord::Logging.error('Must specify filename') exit 1 end plugin_options = options.__hash__ plugin_options[:exclude_messages] = plugin_options[:exclude_messages]&.split(',') plugin_options[:include_messages] = plugin_options[:include_messages]&.split(',') if !(plugin_options[:rbi] || plugin_options[:rbs]) if args.first if args.first.end_with?('.rbi') Sord::Logging.infer('Assuming from filename you wish to generate in RBI format') plugin_options[:rbi] = true elsif args.first.end_with?('.rbs') Sord::Logging.infer('Assuming from filename you wish to generate in RBS format') plugin_options[:rbs] = true else Sord::Logging.error('An output format could not be inferred from your filename; please specify --rbi or --rbs') exit 1 end else Sord::Logging.error('No output format given; please specify --rbi or --rbs') exit 1 end end if (plugin_options[:rbi] && plugin_options[:rbs]) Sord::Logging.error('You cannot specify both --rbi and --rbs; please use only one') exit 1 end plugin = Sord::ParlourPlugin.new(plugin_options) if plugin_options[:rbi] klass = Parlour::RbiGenerator generator_method = :rbi elsif plugin_options[:rbs] klass = Parlour::RbsGenerator generator_method = :rbs end plugin.parlour = klass.new(break_params: plugin_options[:break_params]) plugin.generate(plugin.parlour.root) File.write(args.first, plugin.parlour.send(generator_method)) end end