mime-types-3.1/0000755000004100000410000000000012722123750013477 5ustar www-datawww-datamime-types-3.1/Rakefile0000644000004100000410000001472112722123747015157 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'rubygems' require 'hoe' require 'rake/clean' Hoe.plugin :doofus Hoe.plugin :gemspec2 Hoe.plugin :git Hoe.plugin :minitest Hoe.plugin :travis Hoe.plugin :email unless ENV['CI'] or ENV['TRAVIS'] spec = Hoe.spec 'mime-types' do developer('Austin Ziegler', 'halostatue@gmail.com') self.need_tar = true require_ruby_version '>= 2.0' self.history_file = 'History.rdoc' self.readme_file = 'README.rdoc' license 'MIT' extra_deps << ['mime-types-data', '~> 3.2015'] extra_dev_deps << ['hoe-doofus', '~> 1.0'] extra_dev_deps << ['hoe-gemspec2', '~> 1.1'] extra_dev_deps << ['hoe-git', '~> 1.6'] extra_dev_deps << ['hoe-rubygems', '~> 1.0'] extra_dev_deps << ['hoe-travis', '~> 1.2'] extra_dev_deps << ['minitest', '~> 5.4'] extra_dev_deps << ['minitest-autotest', '~> 1.0'] extra_dev_deps << ['minitest-focus', '~> 1.0'] extra_dev_deps << ['minitest-bonus-assertions', '~> 2.0'] extra_dev_deps << ['minitest-hooks', '~> 1.4'] extra_dev_deps << ['rake', '~> 10.0'] extra_dev_deps << ['fivemat', '~> 1.3' ] extra_dev_deps << ['minitest-rg', '~> 5.2'] if Gem::Version.new(RUBY_VERSION) >= Gem::Version.new('2.0') extra_dev_deps << ['simplecov', '~> 0.7'] # if ENV['CI'] or ENV['TRAVIS'] # extra_dev_deps << ['coveralls', '~> 0.8'] # end end end namespace :benchmark do task :support do %w(lib support).each { |path| $LOAD_PATH.unshift(File.join(Rake.application.original_dir, path)) } end desc 'Benchmark Load Times' task :load, [ :repeats ] => 'benchmark:support' do |_, args| require 'benchmarks/load' Benchmarks::Load.report( File.join(Rake.application.original_dir, 'lib'), args.repeats ) end desc 'Allocation counts' task :allocations, [ :top_x, :mime_types_only ] => 'benchmark:support' do |_, args| require 'benchmarks/load_allocations' Benchmarks::LoadAllocations.report( top_x: args.top_x, mime_types_only: args.mime_types_only ) end desc 'Columnar allocation counts' task 'allocations:columnar', [ :top_x, :mime_types_only ] => 'benchmark:support' do |_, args| require 'benchmarks/load_allocations' Benchmarks::LoadAllocations.report( columnar: true, top_x: args.top_x, mime_types_only: args.mime_types_only ) end desc 'Columnar allocation counts (full load)' task 'allocations:columnar:full', [ :top_x, :mime_types_only ] => 'benchmark:support' do |_, args| require 'benchmarks/load_allocations' Benchmarks::LoadAllocations.report( columnar: true, top_x: args.top_x, mime_types_only: args.mime_types_only, full: true ) end desc 'Object counts' task objects: 'benchmark:support' do require 'benchmarks/object_counts' Benchmarks::ObjectCounts.report end desc 'Columnar object counts' task 'objects:columnar' => 'benchmark:support' do require 'benchmarks/object_counts' Benchmarks::ObjectCounts.report(columnar: true) end desc 'Columnar object counts (full load)' task 'objects:columnar:full' => 'benchmark:support' do require 'benchmarks/object_counts' Benchmarks::ObjectCounts.report(columnar: true, full: true) end end namespace :profile do directory 'tmp/profile' CLEAN.add 'tmp' def ruby_prof(script) require 'pathname' output = Pathname('tmp/profile').join(script) output.mkpath script = Pathname('support/profile').join("#{script}.rb") args = [ '-W0', '-Ilib', '-S', 'ruby-prof', '-R', 'mime/types', '-s', 'self', '-p', 'multi', '-f', "#{output}", script.to_s ] ruby args.join(' ') end task full: 'tmp/profile' do ruby_prof 'full' end task columnar: :support do ruby_prof 'columnar' end task 'columnar:full' => :support do ruby_prof 'columnar_full' end end if Gem::Version.new(RUBY_VERSION) >= Gem::Version.new('2.0') namespace :test do # Coveralls needs to be disabled for now because it transitively depends on # an earlier version of mime-types. # if ENV['CI'] or ENV['TRAVIS'] # task :coveralls do # spec.test_prelude = [ # 'require "psych"', # 'require "simplecov"', # 'require "coveralls"', # 'SimpleCov.formatter = Coveralls::SimpleCov::Formatter', # 'SimpleCov.start("test_frameworks") { command_name "Minitest" }', # 'gem "minitest"' # ].join('; ') # Rake::Task['test'].execute # end # Rake::Task['travis'].prerequisites.replace(%w(test:coveralls)) # end desc 'Run test coverage' task :coverage do spec.test_prelude = [ 'require "simplecov"', 'SimpleCov.start("test_frameworks") { command_name "Minitest" }', 'gem "minitest"' ].join('; ') Rake::Task['test'].execute end end end namespace :convert do namespace :docs do task :setup do gem 'rdoc' require 'rdoc/rdoc' @doc_converter ||= RDoc::Markup::ToMarkdown.new end FileList['*.rdoc'].each do |name| rdoc = name mark = "#{File.basename(name, '.rdoc')}.md" file mark => [ rdoc, :setup ] do |t| puts "#{rdoc} => #{mark}" File.open(t.name, 'wb') { |target| target.write @doc_converter.convert(IO.read(t.prerequisites.first)) } end CLEAN.add mark task run: [ mark ] end end desc 'Convert documentation from RDoc to Markdown' task docs: 'convert:docs:run' end task 'deps:top', [ :number ] do |_, args| require 'net/http' require 'json' def rubygems_get(gem_name: '', endpoint: '') path = File.join('/api/v1/gems/', gem_name, endpoint).chomp('/') + '.json' Net::HTTP.start('rubygems.org', use_ssl: true) do |http| JSON.parse(http.get(path).body) end end results = rubygems_get( gem_name: 'mime-types', endpoint: 'reverse_dependencies' ) weighted_results = {} results.each do |name| begin weighted_results[name] = rubygems_get(gem_name: name)['downloads'] rescue => e puts "#{name} #{e.message}" end end weighted_results.sort { |(_k1, v1), (_k2, v2)| v2 <=> v1 }.first(args.number || 50).each_with_index do |(k, v), i| puts "#{i}) #{k}: #{v}" end end task :console do arguments = %w(pry) arguments.push(*spec.spec.require_paths.map { |dir| "-I#{dir}" }) arguments.push("-r#{spec.spec.name.gsub('-', File::SEPARATOR)}") unless system(*arguments) error "Command failed: #{show_command}" abort end end # vim: syntax=ruby mime-types-3.1/Manifest.txt0000644000004100000410000000127712722123747016023 0ustar www-datawww-dataCode-of-Conduct.rdoc Contributing.rdoc History.rdoc Licence.rdoc Manifest.txt README.rdoc Rakefile lib/mime-types.rb lib/mime/type.rb lib/mime/type/columnar.rb lib/mime/types.rb lib/mime/types/_columnar.rb lib/mime/types/cache.rb lib/mime/types/columnar.rb lib/mime/types/container.rb lib/mime/types/deprecations.rb lib/mime/types/full.rb lib/mime/types/loader.rb lib/mime/types/logger.rb lib/mime/types/registry.rb test/bad-fixtures/malformed test/fixture/json.json test/fixture/old-data test/fixture/yaml.yaml test/minitest_helper.rb test/test_mime_type.rb test/test_mime_types.rb test/test_mime_types_cache.rb test/test_mime_types_class.rb test/test_mime_types_lazy.rb test/test_mime_types_loader.rb mime-types-3.1/Contributing.rdoc0000644000004100000410000000756112722123747017036 0ustar www-datawww-data== Contributing I value any contribution to mime-types you can provide: a bug report, a feature request, or code contributions. There are a few guidelines for contributing to mime-types: * Code changes *will* *not* be accepted without tests. The test suite is written with {Minitest}[https://github.com/seattlerb/minitest]. * Match my coding style. * Use a thoughtfully-named topic branch that contains your change. Rebase your commits into logical chunks as necessary. * Use {quality commit messages}[http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html]. * Do not change the version number; when your patch is accepted and a release is made, the version will be updated at that point. * Submit a GitHub pull request with your changes. * New or changed behaviours require new or updated documentation. === Adding or Modifying MIME Types The mime-types registry is no longer contained in mime-types, but in {mime-types-data}[https://github.com/mime-types/mime-types-data]. Please see that project for contributions there. === Test Dependencies mime-types uses Ryan Davis’s {Hoe}[https://github.com/seattlerb/hoe] to manage the release process, and it adds a number of rake tasks. You will mostly be interested in: $ rake which runs the tests the same way that: $ rake test $ rake travis will do. To assist with the installation of the development dependencies for mime-types, I have provided the simplest possible Gemfile pointing to the (generated) +mime-types.gemspec+ file. This will permit you to do: $ bundle install to get the development dependencies. If you aleady have +hoe+ installed, you can accomplish the same thing with: $ rake newb This task will install any missing dependencies, run the tests/specs, and generate the RDoc. You can run tests with code coverage analysis by running: $ rake test:coverage === Benchmarks mime-types offers several benchmark tasks to measure different measures of performance. There is a repeated load test, measuring how long it takes to start and load mime-types with its full registry. By default, it runs fifty loops and uses the built-in benchmark library. $ rake benchmark:load There are two allocation tracing benchmarks (for normal and columnar loads). These can only be run on Ruby 2.1 or better and requires the {allocation_tracer}[https://github.com/ko1/allocation_tracer] gem (not installed by default). $ rake benchmark:allocations $ rake benchmark:allocations:columnar There are two loaded object count benchmarks (for normal and columnar loads). These use ObjectSpace.count_objects. $ rake benchmark:objects $ rake benchmark:objects:columnar === Workflow Here's the most direct way to get your work merged into the project: * Fork the project. * Clone down your fork (git clone git://github.com//ruby-mime-types.git). * Create a topic branch to contain your change (git checkout -b my\_awesome\_feature). * Hack away, add tests. Not necessarily in that order. * Make sure everything still passes by running +rake+. * If necessary, rebase your commits into logical chunks, without errors. * Push the branch up (git push origin my\_awesome\_feature). * Create a pull request against mime-types/ruby-mime-types and describe what your change does and the why you think it should be merged. === Contributors * Austin Ziegler created mime-types. Thanks to everyone else who has contributed to mime-types: * Aaron Patterson * Aggelos Avgerinos * Andre Pankratz * Andy Brody * Arnaud Meuret * Brandon Galbraith * Chris Gat * David Genord * Eric Marden * Garret Alfert * Godfrey Chan * Greg Brockman * Hans de Graaff * Henrik Hodne * Jeremy Evans * Juanito Fatas * Łukasz Śliwa * Keerthi Siva * Ken Ip * Martin d'Allens * Mauricio Linhares * nycvotes-dev * Postmodern * Richard Hirner * Richard Hurt * Richard Schneeman * Tibor Szolár * Todd Carrico mime-types-3.1/Code-of-Conduct.rdoc0000644000004100000410000000617712722123747017242 0ustar www-datawww-data== Contributor Covenant Code of Conduct ## Our Pledge In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation. === Our Standards Examples of behavior that contributes to creating a positive environment include: * Using welcoming and inclusive language * Being respectful of differing viewpoints and experiences * Gracefully accepting constructive criticism * Focusing on what is best for the community * Showing empathy towards other community members Examples of unacceptable behavior by participants include: * The use of sexualized language or imagery and unwelcome sexual attention or advances * Trolling, insulting/derogatory comments, and personal or political attacks * Public or private harassment * Publishing others' private information, such as a physical or electronic address, without explicit permission * Other conduct which could reasonably be considered inappropriate in a professional setting === Our Responsibilities Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior. Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful. === Scope This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers. === Enforcement Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the project team at [INSERT EMAIL ADDRESS]. All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately. Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership. === Attribution This Code of Conduct is adapted from the {Contributor Covenant}[http://contributor-covenant.org], version 1.4, available at {http://contributor-covenant.org/version/1/4/}[http://contributor-covenant.org/version/1/4/]. mime-types-3.1/History.rdoc0000644000004100000410000007650612722123747016035 0ustar www-datawww-data== 3.1 / 2016-05-22 * 1 documentation change: * Tim Smith (@tas50) updated the build badges to be SVGs to improve readability on high-density (retina) screens with pull request {#112}[https://github.com/mime-types/ruby-mime-types/pull/112]. * 3 bug fixes * A test for MIME::Types::Cache fails under Ruby 2.3 because of frozen strings, {#118}[https://github.com/mime-types/ruby-mime-types/issues/118]. This has been fixed. * The JSON data has been incorrectly encoded since the release of mime-types 3 on the +xrefs+ field, because of the switch to using a Set to store cross-reference information. This has been fixed. * A tentative fix for {#117}[https://github.com/mime-types/ruby-mime-types/issues/117] has been applied, removing the only circular require dependencies that exist (and for which there was code to prevent, but the current fix is simpler). I have no way to verify this fix and depending on how things are loaded by +delayed_job+, this fix may not be sufficient. * 1 governance change * Updated to {Contributor Covenant 1.4}[Code-of-Conduct_rdoc.html]. == 3.0 / 2015-11-21 * 2 governance changes * This project and the related mime-types-data project are now exclusively MIT licensed. Resolves {#95}[https://github.com/mime-types/ruby-mime-types/issues/95]. * All projects under the mime-types organization now have a standard code of conduct adapted from the {Contributor Covenant}[http://contributor-covenant.org]. This text can be found in the {Code-of-Conduct.rdoc}[Code-of-Conduct_rdoc.html] file. * 3 major changes * All methods deprecated in mime-types 2.x have been removed. * mime-types now requires Ruby 2.0 compatibility or later. Resolves {#97}[https://github.com/mime-types/ruby-mime-types/issues/97]. * The registry data has been removed from mime-types and put into mime-types-data, maintained and released separately. It can be found at {mime-types-data}[https://github.com/mime-types/mime-types-data]. * 17 minor changes: * MIME::Type changes: * Changed the way that simplified types representations are creatd to reflect the fact that +x-+ prefixes are no longer considered special according to IANA. A simplified MIME type is case-folded to lowercase. A new keyword parameter, +remove_x_prefix+, can be provided to remove +x-+ prefixes. * Improved initialization with an Array works so that extensions do not need to be wrapped in another array. This means that %w(text/yaml yaml yml) works in the same way that ['text/yaml', %w(yaml yml)] did (and still does). * Changed +priority_compare+ to conform with attributes that no longer exist. * Changed the internal implementation of extensions to use a frozen Set. * When extensions are set or modified with +add_extensions+, the primary registry will be informed of a need to reindex extensions. Resolves {#84}[https://github.com/mime-types/ruby-mime-types/issues/84]. * The preferred extension can be set explicitly. If not set, it will be the first extension. If the preferred extension is not in the extension list, it will be added. * Improved how xref URLs are generated. * Converted +obsolete+, +registered+ and +signature+ to attr_accessors. * MIME::Types changes: * Modified MIME::Types.new to track instances of MIME::Types so that they can be told to reindex the extensions as necessary. * Removed +data_version+ attribute. * Changed #[] so that the +complete+ and +registered+ flags are keywords instead of a generic options parameter. * Extracted the class methods to a separate file. * Changed the container implementation to use a Set instead of an Array to prevent data duplication. Resolves {#79}[https://github.com/mime-types/ruby-mime-types/issues/79]. * MIME::Types::Cache changes: * Caching is now based on the data gem version instead of the mime-types version. * Caching is compatible with columnar registry stores. * MIME::Types::Loader changes: * MIME::Types::Loader::PATH has been removed and replaced with MIME::Types::Data::PATH from the mime-types-data gem. The environment variable RUBY_MIME_TYPES_DATA is still used. * Support for the long-deprecated mime-types v1 format has been removed. * The registry is default loaded from the columnar store by default. The internal format of the columnar store has changed; many of the boolean flags are now loaded from a single file. Resolves {#85}[https://github.com/mime-types/ruby-mime-types/85]. == 2.6.2 / 2015-09-13 * Bugs: * Emilio Losada (@losadaem) fixed an error where +each_with_object+'s block parameters are the inverse of those used by +inject+. Resolves {#107}[https://github.com/mime-types/ruby-mime-types/issues/107] with pull request {#108}[https://github.com/mime-types/ruby-mime-types/pull/108]. * Matt Beedle (@mattbeedle) fixed a typo in MIME::Type::Columnar negatively affecting people who use the +use_instead+ functionality. Resolved in {#109}[https://github.com/mime-types/ruby-mime-types/pull/109]. * Documentation: * Juanito Fatas (@JuanitoFatas) fixed a documentation issue with the README not properly linking internally on the generated rdoc source. Resolved with {#105}[https://github.com/mime-types/ruby-mime-types/pull/105]. * Development: * Fixed a minor issue in the IANA registry parser that would generate empty +text+ xrefs if the +text+ section was empty. == 2.6.1 / 2015-05-25 * Bugs: * Make columnar store handle all supported extensions, not just the first. Resolved in {#103}[https://github.com/mime-types/ruby-mime-types/pull/103] by Jeremy Evans (@jeremyevans). * Avoid circular require when using the columnar store. Resolved in {#102}[https://github.com/mime-types/ruby-mime-types/pull/102] by Jeremy Evans (@jeremyevans). == 2.6 / 2015-05-25 * New Feature: * Columnar data storage for the MIME::Types registry, contributed by Jeremy Evans (@jeremyevans). Reduces default memory use substantially (the mail gem drops from 19 Mib to about 3 Mib). Resolves {#96}[https://github.com/mime-types/ruby-mime-types/pull/96], {#94}[https://github.com/mime-types/ruby-mime-types/issues/94], {#83}[https://github.com/mime-types/ruby-mime-types/issues/83]. Partially addresses {#64}[https://github.com/mime-types/ruby-mime-types/issues/64] and {#62}[https://github.com/mime-types/ruby-mime-types/issues/62]. * Development: * Removed caching of deprecation messages in preparation for mime-types 3.0. Now, deprecated methods will always warn their deprecation instead of only warning once. * Added a logger for deprecation messages. * Renamed lib/mime.rb to lib/mime/deprecations.rb to not conflict with the {mime}[https://rubygems.org/gems/mime] gem on behalf of the maintainers of the {Praxis Framework}[http://praxis-framework.io/]. Provided by Josep M. Blanquer (@blanquer), {#100}[https://github.com/mime-types/ruby-mime-types/pull/100]. * Added the columnar data conversion tool, also provided by Jeremy Evans. * Documentation: * Improved documentation and ensured that all deprecated methods are marked as such in the documentation. * Development: * Added more Ruby variants to Travis CI. * Silenced deprecation messages for internal tools. Noisy deprecations are noisy, but that's the point. == 2.5 / 2015-04-25 * Bugs: * David Genord (@albus522) fixed a bug in loading MIME::Types cache where a container loaded from cache did not have the expected +default_proc+, {#86}[https://github.com/mime-types/ruby-mime-types/pull/86]. * Richard Schneeman (@schneems) provided a patch that substantially reduces unnecessary allocations. * Documentation: * Tibor Szolár (@flexik) fixed a typo in the README, {#82}[https://github.com/mime-types/ruby-mime-types/pull/82] * Fixed {#80}[https://github.com/mime-types/ruby-mime-types/issues/80], clarifying the relationship of MIME::Type#content_type and MIME::Type#simplified, with Ken Ip (@kenips). * Development: * Juanito Fatas (@JuanitoFatas) enabled container mode on Travis CI, {#87}[https://github.com/mime-types/ruby-mime-types/pull/87]. * Moved development to a mime-types organization under {mime-types/ruby-mime-types}[https://github.com/mime-types/ruby-mime-types]. == 2.4.3 / 2014-10-21 * Bugs: * Restored Ruby 1.9.2 support by using +private_constant+ conditionally. Fixes {#77}[https://github.com/mime-types/ruby-mime-types/issues/77] found by Kris Leech (@krisleech). The conditional use of +private_constant+ here will be removed for mime-types 3.0, when Ruby 1.9.2 support will be unconditionally removed. == 2.4.2 / 2014-10-15 * Bugs: * Aaron Patterson (@tenderlove) found a loading bug and provided a fix that nearly doubled registry load performance ({#74}[https://github.com/mime-types/ruby-mime-types/pull/74]). * Godfrey Chan (@chancancode) provided a prophylactic security fix to use JSON.parse instead of JSON.load in {#75}[https://github.com/mime-types/ruby-mime-types/pull/75]. This provides a 20% improvement over the already improved result, resulting in a total 55% performance boost. == 2.4.1 / 2014-10-07 mime-types 2.4 was pulled. * Bugs: * Restored the extension sort order from mime-types 1.25.1 and modified MIME::Type#extensions= to no longer sort extensions when set. This resolves {#71}[https://github.com/mime-types/ruby-mime-types/issues/71] and should fix Paperclip. * API Changes: * Added MIME::Type#preferred_extension to return the preferred extension for the MIME type. This should be used in preference to the current mechanism used by many clients, type.extensions.first. This will allow the implementation to change over time. * Added MIME::Type#friendly based on the concept presented by Łukasz Śliwa’s {friendly_mime}[https://github.com/lukaszsliwa/friendly_mime] gem. The initial English data for this is pulled from +friendly_mime+. * Added MIME::Type#i18n_key and MIME::Type.i18n_key to represent and convert MIME content types as translation keys for the I18n library. * MIME Type Development Tools: * Adding documentation to conversion methods. * Adding some robustness to missing Nokogiri support. * Extending coverage to fully cover new code. Tests now cover all of mime-types. == 2.3 / 2014-05-23 * Bugs: * Fixed a bug in MIME::Types#type_for where type specifications that did not match a MIME::Type would be returned as +nil+ inside the returned array. This was incorrect behaviour as those values should not have been returned, resulting in an empty array. * MIME Type Development Tools: * As always, there are bugs in the IANA registry because it's manually maintained. Some robustness has been added to properly writing file template references where the file template reference is not a full media type specification (e.g., 'amr-wb\+' instead of 'audio/amr-wb\+'). * Both the IANA and Apache import tools were unnecessarily case-sensitive in matching against already-existing MIME types, resulting in extra work to weed out duplicates that differed only in the case of the canonical content type. This has been fixed. == 2.2 / 2014-03-14 * Clarified contribution guidelines for MIME types. Resolves {#57}[https://github.com/mime-types/ruby-mime-types/issues/57]. * Fixed a small bug where deprecated methods would warn of deprecation when called by internal methods. Resolves {#60}[https://github.com/mime-types/ruby-mime-types/issues/60]. * Dropped Code Climate; added Coveralls for test coverage reports. * Removing external references to RubyForge, as it is shutting down. Resolves {#59}[https://github.com/mime-types/ruby-mime-types/issues/59]. == 2.1 / 2014-01-25 * API Changes (MIME::Type): * Added MIME::Type#xrefs and MIME::Type#xref_urls that have better handling of types of reference information. MIME::Type#references= has been deprecated. In a future release, both MIME::Type#references will be turned into a short-hand view on MIME::Type#xrefs, MIME::Type#urls will be an alias for MIME::Type#xref_urls, and MIME::Type#references= will be removed. * New or Updated MIME Types: * This information is now tracked in History-Types.rdoc. * MIME Type Development Tools: * The IANA registry format changed, breaking the IANA registry tool previously used. Rewrote IANADownloader and IANADownloader::Parser as IANARegistryParser using the XML form. * The LTSW list has been dropped as it has not been updated since 2002. * The default Apache MIME types configuration list is now used to enrich MIME type data with additional extension information. == 2.0 / 2013-10-27 * API Changes (General): * mime-types is no longer compatible with Ruby 1.8. Additionally, for its YAML operations (normally development and test), it requires a YAML parser that conforms to the Psych parser, not the Syck parser. This would only be a problem with an alternative Ruby 1.9.2 interpreter that does not implement the Psych parser conventions by requiring +psych+. * MIME::InvalidContentType has been renamed to MIME::Type::InvalidContentType. * API Changes (MIME::Type): * Construction of a MIME::Type can be with any of the following objects: * An array containing a valid content type identifier and an optional array of extensions. This allows MIME::Type.new to be used instead of MIME::Type.from_array for the most common use-case. Fixes {#43}[https://github.com/mime-types/ruby-mime-types/pull/43]. * A Hash containing the output of MIME::Type#to_h, as would be deserialized from the JSON representation of a MIME::Type. This replaces MIME::Type.from_hash using a different parameter set. * Another MIME::Type. * A content type identifier string. * Assignment of an invalid encoding to MIME::Type#encoding= will raise a MIME::Type::InvalidEncoding exception rather than a plain ArgumentError. * MIME::Type#url has been renamed to MIME::Type#references. * MIME::Type#use_instead is now tracked as its own attribute, not as part of MIME::Type#docs. * MIME::Type#system, MIME::Type#system?, MIME::Type#platform?, MIME::Type#to_a, MIME::Type#to_hash, MIME::Type.from_array, MIME::Type.from_hash, and MIME::Type.from_mime_type have been deprecated for removal. * Implemented YAML object encoding and decoding methods, MIME::Type#encode_with and MIME::Type#init_with. * Implemented JSON hash encoding methods. * Added MIME::Type#add_extensions to easily add extensions to a MIME::Type. Fixes {#44}[https://github.com/mime-types/ruby-mime-types/pull/44]. * API Changes (MIME::Types): * MIME type caching has been extracted to its own class. It is structurally similar to what was introduced with mime-types 1.25, but is no longer considered an experimental interface. * MIME type loading has been extracted to its own class. Loading has changed substantially. * MIME::Types#[] accepts a new filter flag, :registered. The :platform flag has been deprecated. * The MIME::Types#type_for platform parameter has been deprecated. * Added the ability for MIME::Types#type_for produce results for multiple filenames or extensions by providing an array as the first parameter. Fixes {#42}[https://github.com/mime-types/ruby-mime-types/pull/42]. * MIME::Types#add_type_variant and MIME::Types#index_extensions have been deprecated as public methods. They will be private in a future version. * MIME::Types#defined_types, MIME::Types.cache_file, MIME::Types.add_type_variant, and MIME::Types.index_extensions have been deprecated for removal. * Default Registry Changes: * The default registry is now a file in the directory data/, located via MIME::Types::Loader::PATH. +PATH+ is defined in the file lib/mime/types/path.rb so that system packagers only have to modify one file in order to put the registry in a location that is not where a gem version of mime-types would expect it. This resolves issue {#36}[https://github.com/mime-types/ruby-mime-types/pull/36], reported by @postmodern. * The default registry is now a single file in JSON format. This resolves issue {#28}[https://github.com/mime-types/ruby-mime-types/pull/28] reported by @jasonlor (an error with mime-types in MacRuby). * The default registry is compiled from YAML files in type-lists/, resolving issue {#37}[https://github.com/mime-types/ruby-mime-types/pull/37] reported by @postmodern requesting an easier-to-edit format. * New or Updated MIME Types: * Major updates to the registered MIME type list from IANA using the improved developer tools. * Added: * application/xhtml\+xml (HTML5) * multipart/x-mixed-replace (HTML5) * application/vnd.apple.pkpass (Apple PassBook) with extension pkpass. * Modified: * application/gzip (RFC6713) added extension (gz) and encoding. * application/epub\+zip is not a registered MIME type. * application/rss\+xml is not a registered MIME type. * application/x-director reported incorrect extensions. * application/x-gzip marked as obsolete (use application/gzip instead). * application/x-maker marked as obsolete (use application/vnd.framemaker instead). * image/webp is not a registered MIME type; added a URL to Google's proposed standard document. * text/html added URL to the HTML5 specification. * text/cache-manifest added URL to the HTML5 specification. * text/plain (VMS .doc files) marked as non-standard. This type will be merged with the standard text/plain type in a future release. * Added md, markdown, rst, and textile extensions to text/plain. * MIME Type Development Tools: * The benchmarking task has been moved mostly to support/benchmarker.rb. * A task for SimpleCov coverage has been added (rake test:coverage). * IANA type registry downloading has been substantially improved and the implementation no longer resides in the Rakefile; it has instead been moved to support/iana_downloader.rb. This takes advantage of the new YAML encoding functionality to update added or modified MIME types non-destructively in type-lists/ by default. * Rake tasks convert:yaml:json and convert:json:yaml provide functionality to convert the human-editable YAML format in type-lists/ to the JSON format in data/ and vice-versa. This is powered by support/convert.rb. == 1.25 / 2013-08-30 * New Features: * Adding lazy loading and caching functionality to the default data based on work done by Greg Brockman (gdb). * Bugs: * Force the default internal application encoding to be used when reading the MIME types database. Based on a change by briangamble, found in the rapid7 fork. * New extensions: * mjpeg (video/x-motion-jpeg) based on a change by punkrats, found in the vidibus fork. * Modernized Minitest configuration. == 1.24 / 2013-08-14 * Code Climate: * Working on improving the quality of the mime-types codebase through the use of Code Climate. * Simplified MIME::Type.from_array to make more assumptions about assignment. * Documentation: * LeoYoung pointed out that the README.rdoc contained examples that could never possibly work because MIME::Types#[] returns (for all the versions I have handy) an array, not a single type. I have updated README.rdoc to reflect this. * Removed Nokogiri as a declared development dependency. It is still required if you're going to use the IANA parser functionality, but it is not necessary for most development purposes. This has been removed to ensure that Travis CI passes on Ruby 1.8.7. * New MIME Types: * 7zip (application/x-7z-compressed). Fixes a request by @kodram. {#32}[https://github.com/mime-types/ruby-mime-types/issues/32] * application/x-www-form-urlencoded. Fixes a request by @alexkwolfe. {#39}[https://github.com/mime-types/ruby-mime-types/issues/39] * Various new MIME types from IANA: * application/mbms-schedule\+xml from 3GPP and Turcotte. * application/provenance\+xml from W3C and Herman. * application/session-info from 3GPP and Firmin. * application/urc-grpsheet\+xml, application/urc-targetdesc\+xml, application/uisocketdesc\+xml from Zimmermann. * application/api\+json from Klabnik. * application/vnd.etsi.pstn\+xml from Han and Belling. * application/vnd.fujixerox.docuworks.container from Tashiro. * application/vnd.windows.devicepairing from Dandawate. * video/vnd.radgamettools.bink and video/vnd.radgamettools.smacker from Andersson. * Updated MIME Types: * RFC 6960 was adopted (application/ocsp-request and application/ocsp-response). == 1.23 / 2013-04-20 * New Feature: * Arnaud Meuret (@ameuret) suggested that it could be useful if the MIME type collection was enumerable, so he implemented it in {#30}[https://github.com/mime-types/ruby-mime-types/pull/30]. Thanks for the contribution! * Updated MIME Types: * RFC6910 was adopted (application/call-completion). * RFC6902 was adopted (application/json-patch\+json). * RFC6917 was adopted (application/mrb-consumer\+xml, application/mrb-publish\+xml). * RFC6922 was adopted (application/sql). * RFC2560 is being {updated}[http://tools.ietf.org/html/draft-ietf-pkix-rfc2560bis]. * Administrivia: * The gemspec now includes information about the licenses under which the mime-types gem is available. * Using hoe-gemspec2 instead of hoe-gemspec. == 1.22 / 2013-03-30 * New MIME Types: * Added support for 3FR (Hasselblad raw images) files. MIME-Type was obtained by looking at exif data with exiftool. Thanks to cgat for these changes. {#27}[https://github.com/mime-types/ruby-mime-types/pull/27] * Updated MIME Types: * Pulled the latest updates from the IANA MIME-Type registry. * Added support for Ruby 2.0 with Travis CI. == 1.21 / 2013-02-09 * New MIME Types: * Various new or updated MIME types by Garret Alfert: application/vnd.ms-fontobject, .eot; application/x-chrome-extension, .crx; application/x-web-app-manifest\+json, .webapp; application/x-xpinstall, .xpi; image/svg\+xml, .svg, .svgz; image/webp, .webp; text/cache-manifest, .appcache, .manifest. #{24}[https://github.com/mime-types/ruby-mime-types/pull/24] * Fixed some Manifest.txt related madness on Travis. == 1.20.1 / 2013-01-26 * New MIME Types: * Apple iWork document types added by Hans de Graaff (application/x-iwork-keynote-sffkey, .key; application/x-iwork-pages-sffpages, .pages; application/x-iwork-numbers-sffnumbers, .numbers). {#20}[https://github.com/mime-types/ruby-mime-types/issue/20] * epub, ibooks, mobi, and DMG content types by Mauricio Linhares (mac:application/x-apple-diskimage, .dmg; application/epub\+zip, .epub; application/x-ibooks\+zip, .ibooks; application/x-mobipocket-ebook, .mobi). {#22}[https://github.com/mime-types/ruby-mime-types/issue/22] * rss content type by Garret Alfert (application/rss\+xml, .rss). {#23}[https://github.com/mime-types/ruby-mime-types/issue/23] * Added or updated MIME types from the latest IANA list. * Fixed MIME Types: * Excel macro-enabled spreadsheets had an incorrect extension. Thanks to Rafael Belvederese for reporting this issue. {#21}[https://github.com/mime-types/ruby-mime-types/issue/21] * Enabled for use with travis. * Enabled gem signing. * Fixed an error related to MIME type downloads. * This was previously published as 1.20, but I had forgotten some attributions. == 1.19 / 2012-06-20 * New MIME Types: * XCF Gnome Images (image/x-xcf, image/x-compressed-xcf; .xcf). {#17}[https://github.com/mime-types/ruby-mime-types/issue/17] * Types reported in {#12}[https://github.com/mime-types/ruby-mime-types/issues/12]: * DV (video/x-dv; .dv) * IVF (video/x-ivf; .ivf) * Matroska (video/x-matroska; .mkv) * Motion JPEG (video/x-motion-jpeg; .mjpg) * RealMedia (official; application/vnd.rn-realmedia; .rm) * New extensions: * dcm (application/dicom); {#16}[https://github.com/mime-types/ruby-mime-types/issue/16]. * Types reported in {#12}[https://github.com/mime-types/ruby-mime-types/issues/12]: * 3g2, 3gpp2 (video/3gpp2) * mpeg (video/mpeg) * mxf (application/mxf) * ts (video/MP2T) * ogg (video/ogg) * Fixed MIME Types: * Adobe AIR application installer packages was missing a hyphen. {#13}[https://github.com/mime-types/ruby-mime-types/issue/13] * Types reported in {#12}[https://github.com/mime-types/ruby-mime-types/issues/12]: * audio/x-pn-realaudio extension is .ra, not .rm. * Resolved {#8}[https://github.com/mime-types/ruby-mime-types/issues/8]. Apparently some people run the tests on Linux. Imagine that. == 1.18 / 2012-03-20 * New MIME Types: * Types reported in #{6}[https://github.com/mime-types/ruby-mime-types/issues/6]: * CoffeeScript (text/x-coffeescript; .coffee; 8bit). * AIR (application/vnd.adobe.air-applicationinstaller-package\+zip, .air; base64). * WOFF (application/font-woff; .woff; base64). * TrueType (application/x-font-truetype; .ttf; base64). * OpenType (application/x-font-opentype; .otf; base64). * WebM (audio/webm, video/webm; .webm). {#11}[https://github.com/mime-types/ruby-mime-types/issues/11.] * New extensions: * f4v/f4p (video/mp4, used by Adobe); f4a/fb4 (audio/mp4, used by Adobe). * Bug Fixes: * It was pointed out that Licence.txt was incorrectly named. Fixed by renaming to Licence.rdoc (from Issue/Pull Request {#8}[https://github.com/mime-types/ruby-mime-types/issues/8]). * It was pointed out that a plan to have the test output generated automatically never went through. {#10}[https://github.com/mime-types/ruby-mime-types/issues/10] == 1.17.2 / 2011-10-25 * Bug Fixes: * Fixed an issue with Ruby 1.9 and file encoding. == 1.17.1 / 2011-10-23 * Minor Enhancements: * Implemented modern 'hoe' semantics. * Switched to minitest instead of test/unit. * Converted documentation from .txt to .rdoc. * Removed setup.rb. {#3}[https://github.com/mime-types/ruby-mime-types/issues/3] * Should no longer complain about missing RubyGems keys {#2}[https://github.com/mime-types/ruby-mime-types/issues/2] * Added .mp4 and .mpg4 as recognized extensions for (application|audio|video)/mp4 per RFC4337. {#1}[https://github.com/mime-types/ruby-mime-types/issues/1] * Added audio/x-aac and .aac per RubyForge issue #28054. * Made it much easier to update MIME types from this point forward. * Updated MIME types from IANA. == 1.16 * Made compatible with Ruby 1.8.6, 1.8.7, and 1.9.1. * Switched to the 'hoe' gem system and added a lot of build-time tools. * Updated the MIME types to the list based on the values in the Perl library version 1.27. Also updated based on external source information and bug reports. * This is the last planned version of MIME::Types 1.x. Work will be starting soon on MIME::Types 2.x with richer data querying mechanisms and support for external data sources. == 1.15 * Removed lib/mime/type.rb to form a single MIME::Types database source. It is unlikely that one will ever need MIME::Type without MIME::Types. * Re-synchronized the MIME type list with the sources, focusing primarily on the IANA list. * Added more detailed source information for MIME::Type objects. * Changed MIME::Types from a module to a class with a default instance. There should be no difference in usage. * Removed MIME::Types::DATA_VERSION; it is now an attribute on the MIME::Types instance. * NOTE: Synchronization with the Perl version of MIME::Types is no longer a priority as of this release. The data format and information has changed. * Removed MIME::Types.by_suffix and MIME::Types.by_mediatype. == 1.13.1 * Fixed a problem with the installer running tests. This now works. * Improved the implementation of MIME::Type.signature? * Moved code around to use the class << self idiom instead of always prepending the module/class name. * Added two new best-guess implementations of functions found in Perl's MIME::Types implementation (1.13). Do not rely on these until the purpose and implementation is stabilised. * Updated the MIME list to reflect changes noted by Ville Skyttä . * Added a new constant to MIME::Types, DATA_VERSION. This will allow the Ruby version number to be updated separately from the Perl version while keeping the MIME Type list version in sync. == 1.13 ! WARNING: This version changes the API of MIME::Types ! ! WARNING: This version is compatible with Ruby 1.8 and higher ONLY ! * Removed dependency on InstallPackage; offering 1.13 as either .tar.gz or .gem. * Split into two files, mime/type.rb and mime/types.rb. This will make maintaining the list of changes easier. * Changed the MIME::Type construction API. Accepts only a single String argument (but does no named type-checking) and yields self. * Removed private methods #init_extensions, #init_encoding, and #init_system and replaced with #extensions=, #encoding=, and #system=. * Added #default_encoding to return 'quoted-printable' or 'base64' depending on the media type of the MIME type. * Added #raw_media_type and #raw_sub_type to provide the non-simplified versions of the media type and subtype. * Alternative constructors MIME::Type.from_array, MIME::Type.from_hash, and MIME::Type.from_mime_type added to compensate for the removal of named type checking in the original constructor. * Added #to_str, #to_a, and #to_hash methods. The latter two will provide output suitable for use in #from_array and #from_hash. * Removed "binary" encoding and enforced the use of a valid encoding string. * Added #system? returning true if the MIME::Type is an OS-specific MIME::Type. * Added #platform? returning true if the MIME::Type is an OS-specific MIME::Type for the current RUBY_PLATFORM. * Added #like? returning true if the simplified type matches the other value provided. #<'application/x-excel'>.like?('application/excel') is true. * Added #complete? returning true if the MIME::Type specifies an extension list. * Updated the MIME type list to reflect additions by Mark Overmeer for Perl's MIME::Types 1.12 and the official IANA list as of 2004.04.06. A number of formerly "registered" MIME types are now no longer registered (e.g., application/excel is now application/x-excel). This ensures that the simplified type still works with applications, but does not report an unregistered type as registered. * Restored MIME type list to Mark Overmeer's format to facilitate easy exchange between the two projects. * Added additional unit tests from Mark Overmeer's 1.12 version. == 1.07 * Changed version numbering to match Perl MIME::Types 1.07. * Re-synchronized with Mark Overmeer's list in Perl PMIME::Types 1.07. * [NN Poster] updated the attributes for the PGP types. == 1.005 * Changed to Phil Thomson's InstallPackage. * Added several types from Perl MIME::Types 1.005. * Cleaned up data format; some data formats will show up with proper data now. == 1.004 * Updated to match Perl MIME::Types 1.004, links credited to Dan Puro. Adds new reference list to http://www.indiana.edu/cgi-bin-local/mimetypes * Removed InvalidType and replaced with TypeError. * Changed instances of #type to #class. * Cleaned up how simplified versions are created. == 1.003 * Initial release based on Perl MIME::Types 1.003. mime-types-3.1/Licence.rdoc0000644000004100000410000000224212722123747015720 0ustar www-datawww-data== Licence * Copyright 2003–2015 Austin Ziegler and contributors. The software in this repository is made available under the MIT license. === MIT License Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. mime-types-3.1/README.rdoc0000644000004100000410000002163012722123747015315 0ustar www-datawww-data= mime-types for Ruby home :: https://github.com/mime-types/ruby-mime-types/ code :: https://github.com/mime-types/ruby-mime-types/ bugs :: https://github.com/mime-types/ruby-mime-types/issues rdoc :: http://rdoc.info/gems/mime-types/ continuous integration :: {Build Status}[https://travis-ci.org/mime-types/ruby-mime-types] test coverage :: {Coverage Status}[https://coveralls.io/github/mime-types/ruby-mime-types?branch=master] == Description The mime-types library provides a library and registry for information about MIME content type definitions. It can be used to determine defined filename extensions for MIME types, or to use filename extensions to look up the likely MIME type definitions. Version 3.0 is a major release that requires Ruby 2.0 compatibility and removes deprecated functions. The columnar registry format introduced in 2.6 has been made the primary format; the registry data has been extracted from this library and put into {mime-types-data}[https://github.com/mime-types/mime-types-data]. Additionally, mime-types is now licensed exclusively under the MIT licence and there is a code of conduct in effect. There are a number of other smaller changes described in the History file. === About MIME Media Types MIME content types are used in MIME-compliant communications, as in e-mail or HTTP traffic, to indicate the type of content which is transmitted. The mime-types library provides the ability for detailed information about MIME entities (provided as an enumerable collection of MIME::Type objects) to be determined and used. There are many types defined by RFCs and vendors, so the list is long but by definition incomplete; don't hesitate to add additional type definitions. MIME type definitions found in mime-types are from RFCs, W3C recommendations, the {IANA Media Types registry}[https://www.iana.org/assignments/media-types/media-types.xhtml], and user contributions. It conforms to RFCs 2045 and 2231. === mime-types 1.x End of Life mime-types 1.x is no longer supported as of 2015-10-27. === mime-types 2.x End of Life mime-types 2.x is supported as 2.99.x receiving quarterly updates of the IANA registry and security updates for two years. It will reach full end of life on 2017-11-21. === mime-types 3.x Users are encouraged to upgrade to mime-types 3.x as soon as is practical. mime-types 3.x requires Ruby 2.0 compatibility and a simpler licensing scheme. == Synopsis MIME types are used in MIME entities, as in email or HTTP traffic. It is useful at times to have information available about MIME types (or, inversely, about files). A MIME::Type stores the known information about one MIME type. require 'mime/types' plaintext = MIME::Types['text/plain'] # => [ text/plain ] text = plaintext.first puts text.media_type # => 'text' puts text.sub_type # => 'plain' puts text.extensions.join(' ') # => 'txt asc c cc h hh cpp hpp dat hlp' puts text.preferred_extension # => 'txt' puts text.friendly # => 'Text Document' puts text.i18n_key # => 'text.plain' puts text.encoding # => quoted-printable puts text.default_encoding # => quoted-printable puts text.binary? # => false puts text.ascii? # => true puts text.obsolete? # => false puts text.registered? # => true puts text.complete? # => true puts text # => 'text/plain' puts text == 'text/plain' # => true puts 'text/plain' == text # => true puts text == 'text/x-plain' # => false puts 'text/x-plain' == text # => false puts MIME::Type.simplified('x-appl/x-zip') # => 'x-appl/x-zip' puts MIME::Type.i18n_key('x-appl/x-zip') # => 'x-appl.x-zip' puts text.like?('text/x-plain') # => true puts text.like?(MIME::Type.new('x-text/x-plain')) # => true puts text.xrefs.inspect # => { "rfc" => [ "rfc2046", "rfc3676", "rfc5147" ] } puts text.xref_urls # => [ "http://www.iana.org/go/rfc2046", # "http://www.iana.org/go/rfc3676", # "http://www.iana.org/go/rfc5147" ] xtext = MIME::Type.new('x-text/x-plain') puts xtext.media_type # => 'text' puts xtext.raw_media_type # => 'x-text' puts xtext.sub_type # => 'plain' puts xtext.raw_sub_type # => 'x-plain' puts xtext.complete? # => false puts MIME::Types.any? { |type| type.content_type == 'text/plain' } # => true puts MIME::Types.all?(&:registered?) # => false # Various string representations of MIME types qcelp = MIME::Types['audio/QCELP'].first # => audio/QCELP puts qcelp.content_type # => 'audio/QCELP' puts qcelp.simplified # => 'audio/qcelp' xwingz = MIME::Types['application/x-Wingz'].first # => application/x-Wingz puts xwingz.content_type # => 'application/x-Wingz' puts xwingz.simplified # => 'application/x-wingz' === Columnar Store mime-types uses as its primary registry storage format a columnar storage format reducing the default memory footprint. This is done by selectively loading the data on a per-attribute basis. When the registry is first loaded from the columnar store, only the canonical MIME content type and known extensions and the MIME type will be connected to its loading registry. When other data about the type is required (including +preferred_extension+, obsolete?, and registered?) that data is loaded from its own column file for all types in the registry. The load of any column data is performed with a Mutex to ensure that types are updated safely in a multithreaded environment. Benchmarks show that while columnar data loading is slower than the JSON store, it cuts the memory use by a third over the JSON store. If you prefer to load all the data at once, this can be specified in your application Gemfile as: gem 'mime-types', require: 'mime/types/full' Projects that do not use Bundler should +require+ the same: require 'mime/types/full' Libraries that use mime-types are discouraged from choosing the JSON store. For applications and clients that used mime-types 2.6 when the columnar store was introduced, the require used previously will still work through at least {version 4}[https://github.com/mime-types/ruby-mime-types/pull/96#issuecomment-100725400] and possibly beyond; it is effectively an empty operation. You are recommended to change your Gemfile as soon as is practical. require 'mime/types/columnar' Note that MIME::Type::Columnar and MIME::Types::Columnar are considered private variant implementations of MIME::Type and MIME::Types and the specific implementation should not be relied upon by consumers of the mime-types library. Instead, depend on the public implementations (MIME::Type and MIME::Types) only. === Cached Storage mime-types supports a cache of MIME types using Marshal.dump. The cache is invalidated for each version of the mime-types-data gem so that data version 3.2015.1201 will not be reused with data version 3.2016.0101. If the environment variable +RUBY_MIME_TYPES_CACHE+ is set to a cache file, mime-types will attempt to load the MIME type registry from the cache file. If it cannot, it will load the types normally and then saves the registry to the cache file. The caching works with both full stores and columnar stores. Only the data that has been loaded prior to saving the cache will be stored. == mime-types Modified Semantic Versioning The mime-types library has one version number, but this single version number tracks both API changes and registry data changes; this is not wholly compatible with all aspects of {Semantic Versioning}[http://semver.org/]; removing a MIME type from the registry *could* be considered a breaking change under some interpretations of semantic versioning (as lookups for that particular type would no longer work by default). mime-types uses a modified semantic versioning scheme. Given the version MAJOR.MINOR: 1. If an incompatible API (code) change is made, the MAJOR version will be incremented, MINOR will be set to zero, and PATCH will be reset to the implied zero. 2. If an API (code) feature is added that does not break compatibilty, the MINOR version will be incremented and PATCH will be reset to the implied zero. 3. If there is a bugfix to a feature added in the most recent MAJOR.MINOR release, the implied PATCH value will be incremented resulting in MAJOR.MINOR.PATCH. In practical terms, there will be fewer releases of mime-types focussing on features because of the existence of the [mime-types-data][] gem, and if features are marked deprecated in the course of mime-types 3.x, they will not be removed until mime-types 4.x or possibly later. :include: Code-of-Conduct.rdoc :include: Contributing.rdoc :include: Licence.rdoc mime-types-3.1/lib/0000755000004100000410000000000012722123747014253 5ustar www-datawww-datamime-types-3.1/lib/mime-types.rb0000644000004100000410000000002512722123747016666 0ustar www-datawww-datarequire 'mime/types' mime-types-3.1/lib/mime/0000755000004100000410000000000012722123747015202 5ustar www-datawww-datamime-types-3.1/lib/mime/type/0000755000004100000410000000000012722123747016163 5ustar www-datawww-datamime-types-3.1/lib/mime/type/columnar.rb0000644000004100000410000000311212722123747020325 0ustar www-datawww-datarequire 'mime/type' # A version of MIME::Type that works hand-in-hand with a MIME::Types::Columnar # container to load data by columns. # # When a field is has not yet been loaded, that data will be loaded for all # types in the container before forwarding the message to MIME::Type. # # More information can be found in MIME::Types::Columnar. # # MIME::Type::Columnar is *not* intended to be created except by # MIME::Types::Columnar containers. class MIME::Type::Columnar < MIME::Type def initialize(container, content_type, extensions) # :nodoc: @container = container self.content_type = content_type self.extensions = extensions end def self.column(*methods, file: nil) # :nodoc: file = methods.first unless file file_method = :"load_#{file}" methods.each do |m| define_method m do |*args| @container.send(file_method) super(*args) end end end column :friendly column :encoding, :encoding= column :docs, :docs= column :preferred_extension, :preferred_extension= column :obsolete, :obsolete=, :obsolete?, :registered, :registered=, :registered?, :signature, :signature=, :signature?, file: 'flags' column :xrefs, :xrefs=, :xref_urls column :use_instead, :use_instead= def encode_with(coder) # :nodoc: @container.send(:load_friendly) @container.send(:load_encoding) @container.send(:load_docs) @container.send(:load_flags) @container.send(:load_use_instead) @container.send(:load_xrefs) @container.send(:load_preferred_extension) super end class << self undef column end end mime-types-3.1/lib/mime/types.rb0000644000004100000410000001735712722123747016710 0ustar www-datawww-data## module MIME ## class Types end end require 'mime/type' # MIME::Types is a registry of MIME types. It is both a class (created with # MIME::Types.new) and a default registry (loaded automatically or through # interactions with MIME::Types.[] and MIME::Types.type_for). # # == The Default mime-types Registry # # The default mime-types registry is loaded automatically when the library # is required (require 'mime/types'), but it may be lazily loaded # (loaded on first use) with the use of the environment variable # +RUBY_MIME_TYPES_LAZY_LOAD+ having any value other than +false+. The # initial startup is about 14× faster (~10 ms vs ~140 ms), but the # registry will be loaded at some point in the future. # # The default mime-types registry can also be loaded from a Marshal cache # file specific to the version of MIME::Types being loaded. This will be # handled automatically with the use of a file referred to in the # environment variable +RUBY_MIME_TYPES_CACHE+. MIME::Types will attempt to # load the registry from this cache file (MIME::Type::Cache.load); if it # cannot be loaded (because the file does not exist, there is an error, or # the data is for a different version of mime-types), the default registry # will be loaded from the normal JSON version and then the cache file will # be *written* to the location indicated by +RUBY_MIME_TYPES_CACHE+. Cache # file loads just over 4½× faster (~30 ms vs ~140 ms). # loads. # # Notes: # * The loading of the default registry is *not* atomic; when using a # multi-threaded environment, it is recommended that lazy loading is not # used and mime-types is loaded as early as possible. # * Cache files should be specified per application in a multiprocess # environment and should be initialized during deployment or before # forking to minimize the chance that the multiple processes will be # trying to write to the same cache file at the same time, or that two # applications that are on different versions of mime-types would be # thrashing the cache. # * Unless cache files are preinitialized, the application using the # mime-types cache file must have read/write permission to the cache file. # # == Usage # require 'mime/types' # # plaintext = MIME::Types['text/plain'] # print plaintext.media_type # => 'text' # print plaintext.sub_type # => 'plain' # # puts plaintext.extensions.join(" ") # => 'asc txt c cc h hh cpp' # # puts plaintext.encoding # => 8bit # puts plaintext.binary? # => false # puts plaintext.ascii? # => true # puts plaintext.obsolete? # => false # puts plaintext.registered? # => true # puts plaintext == 'text/plain' # => true # puts MIME::Type.simplified('x-appl/x-zip') # => 'appl/zip' # class MIME::Types # The release version of Ruby MIME::Types VERSION = MIME::Type::VERSION include Enumerable # Creates a new MIME::Types registry. def initialize @type_variants = Container.new @extension_index = Container.new end # Returns the number of known type variants. def count @type_variants.values.inject(0) { |a, e| a + e.size } end def inspect # :nodoc: "#<#{self.class}: #{count} variants, #{@extension_index.count} extensions>" end # Iterates through the type variants. def each if block_given? @type_variants.each_value { |tv| tv.each { |t| yield t } } else enum_for(:each) end end @__types__ = nil # Returns a list of MIME::Type objects, which may be empty. The optional # flag parameters are :complete (finds only complete MIME::Type # objects) and :registered (finds only MIME::Types that are # registered). It is possible for multiple matches to be returned for # either type (in the example below, 'text/plain' returns two values -- # one for the general case, and one for VMS systems). # # puts "\nMIME::Types['text/plain']" # MIME::Types['text/plain'].each { |t| puts t.to_a.join(", ") } # # puts "\nMIME::Types[/^image/, complete: true]" # MIME::Types[/^image/, :complete => true].each do |t| # puts t.to_a.join(", ") # end # # If multiple type definitions are returned, returns them sorted as # follows: # 1. Complete definitions sort before incomplete ones; # 2. IANA-registered definitions sort before LTSW-recorded # definitions. # 3. Current definitions sort before obsolete ones; # 4. Obsolete definitions with use-instead clauses sort before those # without; # 5. Obsolete definitions use-instead clauses are compared. # 6. Sort on name. def [](type_id, complete: false, registered: false) matches = case type_id when MIME::Type @type_variants[type_id.simplified] when Regexp match(type_id) else @type_variants[MIME::Type.simplified(type_id)] end prune_matches(matches, complete, registered).sort { |a, b| a.priority_compare(b) } end # Return the list of MIME::Types which belongs to the file based on its # filename extension. If there is no extension, the filename will be used # as the matching criteria on its own. # # This will always return a merged, flatten, priority sorted, unique array. # # puts MIME::Types.type_for('citydesk.xml') # => [application/xml, text/xml] # puts MIME::Types.type_for('citydesk.gif') # => [image/gif] # puts MIME::Types.type_for(%w(citydesk.xml citydesk.gif)) # => [application/xml, image/gif, text/xml] def type_for(filename) Array(filename).flat_map { |fn| @extension_index[fn.chomp.downcase[/\.?([^.]*?)$/, 1]] }.compact.inject(:+).sort { |a, b| a.priority_compare(b) } end alias_method :of, :type_for # Add one or more MIME::Type objects to the set of known types. If the # type is already known, a warning will be displayed. # # The last parameter may be the value :silent or +true+ which # will suppress duplicate MIME type warnings. def add(*types) quiet = ((types.last == :silent) or (types.last == true)) types.each do |mime_type| case mime_type when true, false, nil, Symbol nil when MIME::Types variants = mime_type.instance_variable_get(:@type_variants) add(*variants.values.inject(:+).to_a, quiet) when Array add(*mime_type, quiet) else add_type(mime_type, quiet) end end end # Add a single MIME::Type object to the set of known types. If the +type+ is # already known, a warning will be displayed. The +quiet+ parameter may be a # truthy value to suppress that warning. def add_type(type, quiet = false) if !quiet and @type_variants[type.simplified].include?(type) MIME::Types.logger.warn <<-warning Type #{type} is already registered as a variant of #{type.simplified}. warning end add_type_variant!(type) index_extensions!(type) end private def add_type_variant!(mime_type) @type_variants[mime_type.simplified] << mime_type end def reindex_extensions!(mime_type) return unless @type_variants[mime_type.simplified].include?(mime_type) index_extensions!(mime_type) end def index_extensions!(mime_type) mime_type.extensions.each { |ext| @extension_index[ext] << mime_type } end def prune_matches(matches, complete, registered) matches.delete_if { |e| !e.complete? } if complete matches.delete_if { |e| !e.registered? } if registered matches end def match(pattern) @type_variants.select { |k, _| k =~ pattern }.values.inject(:+) end end require 'mime/types/cache' require 'mime/types/container' require 'mime/types/loader' require 'mime/types/logger' require 'mime/types/_columnar' require 'mime/types/registry' mime-types-3.1/lib/mime/types/0000755000004100000410000000000012722123747016346 5ustar www-datawww-datamime-types-3.1/lib/mime/types/cache.rb0000644000004100000410000000401712722123747017740 0ustar www-datawww-dataMIME::Types::Cache = Struct.new(:version, :data) # :nodoc: # Caching of MIME::Types registries is advisable if you will be loading # the default registry relatively frequently. With the class methods on # MIME::Types::Cache, any MIME::Types registry can be marshaled quickly # and easily. # # The cache is invalidated on a per-data-version basis; a cache file for # version 3.2015.1118 will not be reused with version 3.2015.1201. class << MIME::Types::Cache # Attempts to load the cache from the file provided as a parameter or in # the environment variable +RUBY_MIME_TYPES_CACHE+. Returns +nil+ if the # file does not exist, if the file cannot be loaded, or if the data in # the cache version is different than this version. def load(cache_file = nil) cache_file ||= ENV['RUBY_MIME_TYPES_CACHE'] return nil unless cache_file and File.exist?(cache_file) cache = Marshal.load(File.binread(cache_file)) if cache.version == MIME::Types::Data::VERSION Marshal.load(cache.data) else MIME::Types.logger.warn <<-warning.chomp Could not load MIME::Types cache: invalid version warning nil end rescue => e MIME::Types.logger.warn <<-warning.chomp Could not load MIME::Types cache: #{e} warning return nil end # Attempts to save the types provided to the cache file provided. # # If +types+ is not provided or is +nil+, the cache will contain the # current MIME::Types default registry. # # If +cache_file+ is not provided or is +nil+, the cache will be written # to the file specified in the environment variable # +RUBY_MIME_TYPES_CACHE+. If there is no cache file specified either # directly or through the environment, this method will return +nil+ def save(types = nil, cache_file = nil) cache_file ||= ENV['RUBY_MIME_TYPES_CACHE'] return nil unless cache_file types ||= MIME::Types.send(:__types__) File.open(cache_file, 'wb') do |f| f.write( Marshal.dump(new(MIME::Types::Data::VERSION, Marshal.dump(types))) ) end end end mime-types-3.1/lib/mime/types/loader.rb0000644000004100000410000001052112722123747020140 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- ## module MIME; end ## class MIME::Types; end require 'mime/types/data' # This class is responsible for initializing the MIME::Types registry from # the data files supplied with the mime-types library. # # The Loader will use one of the following paths: # 1. The +path+ provided in its constructor argument; # 2. The value of ENV['RUBY_MIME_TYPES_DATA']; or # 3. The value of MIME::Types::Data::PATH. # # When #load is called, the +path+ will be searched recursively for all YAML # (.yml or .yaml) files. By convention, there is one file for each media # type (application.yml, audio.yml, etc.), but this is not required. class MIME::Types::Loader # The path that will be read for the MIME::Types files. attr_reader :path # The MIME::Types container instance that will be loaded. If not provided # at initialization, a new MIME::Types instance will be constructed. attr_reader :container # Creates a Loader object that can be used to load MIME::Types registries # into memory, using YAML, JSON, or Columnar registry format loaders. def initialize(path = nil, container = nil) path = path || ENV['RUBY_MIME_TYPES_DATA'] || MIME::Types::Data::PATH @container = container || MIME::Types.new @path = File.expand_path(path) # begin # require 'mime/lazy_types' # @container.extend(MIME::LazyTypes) # end end # Loads a MIME::Types registry from YAML files (*.yml or # *.yaml) recursively found in +path+. # # It is expected that the YAML objects contained within the registry array # will be tagged as !ruby/object:MIME::Type. # # Note that the YAML format is about 2½ times *slower* than the JSON format. # # NOTE: The purpose of this format is purely for maintenance reasons. def load_yaml Dir[yaml_path].sort.each do |f| container.add(*self.class.load_from_yaml(f), :silent) end container end # Loads a MIME::Types registry from JSON files (*.json) # recursively found in +path+. # # It is expected that the JSON objects will be an array of hash objects. # The JSON format is the registry format for the MIME types registry # shipped with the mime-types library. def load_json Dir[json_path].sort.each do |f| types = self.class.load_from_json(f) container.add(*types, :silent) end container end # Loads a MIME::Types registry from columnar files recursively found in # +path+. def load_columnar require 'mime/types/columnar' unless defined?(MIME::Types::Columnar) container.extend(MIME::Types::Columnar) container.load_base_data(path) container end # Loads a MIME::Types registry. Loads from JSON files by default # (#load_json). # # This will load from columnar files (#load_columnar) if columnar: # true is provided in +options+ and there are columnar files in +path+. def load(options = { columnar: false }) if options[:columnar] && !Dir[columnar_path].empty? load_columnar else load_json end end class << self # Loads the default MIME::Type registry. def load(options = { columnar: false }) new.load(options) end # Loads MIME::Types from a single YAML file. # # It is expected that the YAML objects contained within the registry # array will be tagged as !ruby/object:MIME::Type. # # Note that the YAML format is about 2½ times *slower* than the JSON # format. # # NOTE: The purpose of this format is purely for maintenance reasons. def load_from_yaml(filename) begin require 'psych' rescue LoadError nil end require 'yaml' YAML.load(read_file(filename)) end # Loads MIME::Types from a single JSON file. # # It is expected that the JSON objects will be an array of hash objects. # The JSON format is the registry format for the MIME types registry # shipped with the mime-types library. def load_from_json(filename) require 'json' JSON.parse(read_file(filename)).map { |type| MIME::Type.new(type) } end private def read_file(filename) File.open(filename, 'r:UTF-8:-', &:read) end end private def yaml_path File.join(path, '*.y{,a}ml') end def json_path File.join(path, '*.json') end def columnar_path File.join(path, '*.column') end end mime-types-3.1/lib/mime/types/_columnar.rb0000644000004100000410000000624712722123747020663 0ustar www-datawww-datarequire 'mime/type/columnar' # MIME::Types::Columnar is used to extend a MIME::Types container to load data # by columns instead of from JSON or YAML. Column loads of MIME types loaded # through the columnar store are synchronized with a Mutex. # # MIME::Types::Columnar is not intended to be used directly, but will be added # to an instance of MIME::Types when it is loaded with # MIME::Types::Loader#load_columnar. module MIME::Types::Columnar LOAD_MUTEX = Mutex.new # :nodoc: def self.extended(obj) # :nodoc: super obj.instance_variable_set(:@__mime_data__, []) obj.instance_variable_set(:@__files__, Set.new) end # Load the first column data file (type and extensions). def load_base_data(path) #:nodoc: @__root__ = path each_file_line('content_type', false) do |line| line = line.split content_type = line.shift extensions = line # content_type, *extensions = line.split type = MIME::Type::Columnar.new(self, content_type, extensions) @__mime_data__ << type add(type) end self end private def each_file_line(name, lookup = true) LOAD_MUTEX.synchronize do next if @__files__.include?(name) i = -1 column = File.join(@__root__, "mime.#{name}.column") IO.readlines(column, encoding: 'UTF-8'.freeze).each do |line| line.chomp! if lookup type = @__mime_data__[i += 1] or next yield type, line else yield line end end @__files__ << name end end def load_encoding each_file_line('encoding') do |type, line| pool ||= {} line.freeze type.instance_variable_set(:@encoding, (pool[line] ||= line)) end end def load_docs each_file_line('docs') do |type, line| type.instance_variable_set(:@docs, opt(line)) end end def load_preferred_extension each_file_line('pext') do |type, line| type.instance_variable_set(:@preferred_extension, opt(line)) end end def load_flags each_file_line('flags') do |type, line| line = line.split type.instance_variable_set(:@obsolete, flag(line.shift)) type.instance_variable_set(:@registered, flag(line.shift)) type.instance_variable_set(:@signature, flag(line.shift)) end end def load_xrefs each_file_line('xrefs') { |type, line| type.instance_variable_set(:@xrefs, dict(line, array: true)) } end def load_friendly each_file_line('friendly') { |type, line| type.instance_variable_set(:@friendly, dict(line)) } end def load_use_instead each_file_line('use_instead') do |type, line| type.instance_variable_set(:@use_instead, opt(line)) end end def dict(line, array: false) if line == '-'.freeze {} else line.split('|'.freeze).each_with_object({}) { |l, h| k, v = l.split('^'.freeze) v = nil if v.empty? h[k] = array ? Array(v) : v } end end def arr(line) if line == '-'.freeze [] else line.split('|'.freeze).flatten.compact.uniq end end def opt(line) line unless line == '-'.freeze end def flag(line) line == '1'.freeze ? true : false end end mime-types-3.1/lib/mime/types/deprecations.rb0000644000004100000410000000155612722123747021362 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types/logger' # The namespace for MIME applications, tools, and libraries. module MIME ## class Types # Used to mark a method as deprecated in the mime-types interface. def self.deprecated(klass, sym, message = nil, &block) # :nodoc: level = case klass when Class, Module '.' else klass = klass.class '#' end message = case message when :private, :protected "and will be #{message}" when nil 'and will be removed' else message end MIME::Types.logger.warn <<-warning.chomp #{caller[1]}: #{klass}#{level}#{sym} is deprecated #{message}. warning block.call if block end end end mime-types-3.1/lib/mime/types/container.rb0000644000004100000410000000135712722123747020663 0ustar www-datawww-datarequire 'set' # MIME::Types requires a container Hash with a default values for keys # resulting in an empty array ([]), but this cannot be dumped through # Marshal because of the presence of that default Proc. This class exists # solely to satisfy that need. class MIME::Types::Container < Hash # :nodoc: def initialize super self.default_proc = ->(h, k) { h[k] = Set.new } end def marshal_dump {}.merge(self) end def marshal_load(hash) self.default_proc = ->(h, k) { h[k] = Set.new } merge!(hash) end def encode_with(coder) each { |k, v| coder[k] = v.to_a } end def init_with(coder) self.default_proc = ->(h, k) { h[k] = Set.new } coder.map.each { |k, v| self[k] = Set[*v] } end end mime-types-3.1/lib/mime/types/logger.rb0000644000004100000410000000134112722123747020151 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'logger' ## module MIME ## class Types class << self # Configure the MIME::Types logger. This defaults to an instance of a # logger that passes messages (unformatted) through to Kernel#warn. attr_accessor :logger end class WarnLogger < ::Logger #:nodoc: class WarnLogDevice < ::Logger::LogDevice #:nodoc: def initialize(*) end def write(m) Kernel.warn(m) end def close end end def initialize(_1, _2 = nil, _3 = nil) super nil @logdev = WarnLogDevice.new @formatter = ->(_s, _d, _p, m) { m } end end self.logger = WarnLogger.new(nil) end end mime-types-3.1/lib/mime/types/full.rb0000644000004100000410000000035012722123747017633 0ustar www-datawww-data## module MIME ## class Types unless private_method_defined?(:load_mode) class << self private def load_mode { columnar: false } end end end end end require 'mime/types' mime-types-3.1/lib/mime/types/registry.rb0000644000004100000410000000324112722123747020543 0ustar www-datawww-dataclass << MIME::Types include Enumerable ## def new(*) # :nodoc: super.tap do |types| __instances__.add types end end # MIME::Types#[] against the default MIME::Types registry. def [](type_id, complete: false, registered: false) __types__[type_id, complete: complete, registered: registered] end # MIME::Types#count against the default MIME::Types registry. def count __types__.count end # MIME::Types#each against the default MIME::Types registry. def each if block_given? __types__.each { |t| yield t } else enum_for(:each) end end # MIME::Types#type_for against the default MIME::Types registry. def type_for(filename) __types__.type_for(filename) end alias_method :of, :type_for # MIME::Types#add against the default MIME::Types registry. def add(*types) __types__.add(*types) end private def lazy_load? (lazy = ENV['RUBY_MIME_TYPES_LAZY_LOAD']) && (lazy != 'false') end def __types__ (defined?(@__types__) and @__types__) or load_default_mime_types end unless private_method_defined?(:load_mode) def load_mode { columnar: true } end end def load_default_mime_types(mode = load_mode) @__types__ = MIME::Types::Cache.load unless @__types__ @__types__ = MIME::Types::Loader.load(mode) MIME::Types::Cache.save(@__types__) end @__types__ end def __instances__ @__instances__ ||= Set.new end def reindex_extensions(type) __instances__.each do |instance| instance.send(:reindex_extensions!, type) end true end end ## class MIME::Types load_default_mime_types(load_mode) unless lazy_load? end mime-types-3.1/lib/mime/types/columnar.rb0000644000004100000410000000002512722123747020510 0ustar www-datawww-datarequire 'mime/types' mime-types-3.1/lib/mime/type.rb0000644000004100000410000004221012722123747016507 0ustar www-datawww-data## module MIME end # The definition of one MIME content-type. # # == Usage # require 'mime/types' # # plaintext = MIME::Types['text/plain'].first # # returns [text/plain, text/plain] # text = plaintext.first # print text.media_type # => 'text' # print text.sub_type # => 'plain' # # puts text.extensions.join(" ") # => 'asc txt c cc h hh cpp' # # puts text.encoding # => 8bit # puts text.binary? # => false # puts text.ascii? # => true # puts text == 'text/plain' # => true # puts MIME::Type.simplified('x-appl/x-zip') # => 'appl/zip' # # puts MIME::Types.any? { |type| # type.content_type == 'text/plain' # } # => true # puts MIME::Types.all?(&:registered?) # # => false class MIME::Type # Reflects a MIME content-type specification that is not correctly # formatted (it isn't +type+/+subtype+). class InvalidContentType < ArgumentError # :stopdoc: def initialize(type_string) @type_string = type_string end def to_s "Invalid Content-Type #{@type_string.inspect}" end # :startdoc: end # Reflects an unsupported MIME encoding. class InvalidEncoding < ArgumentError # :stopdoc: def initialize(encoding) @encoding = encoding end def to_s "Invalid Encoding #{@encoding.inspect}" end # :startdoc: end # The released version of the mime-types library. VERSION = '3.1' include Comparable # :stopdoc: # TODO verify mime-type character restrictions; I am pretty sure that this is # too wide open. MEDIA_TYPE_RE = %r{([-\w.+]+)/([-\w.+]*)} I18N_RE = %r{[^[:alnum:]]} BINARY_ENCODINGS = %w(base64 8bit) ASCII_ENCODINGS = %w(7bit quoted-printable) # :startdoc: private_constant :MEDIA_TYPE_RE, :I18N_RE, :BINARY_ENCODINGS, :ASCII_ENCODINGS # Builds a MIME::Type object from the +content_type+, a MIME Content Type # value (e.g., 'text/plain' or 'applicaton/x-eruby'). The constructed object # is yielded to an optional block for additional configuration, such as # associating extensions and encoding information. # # * When provided a Hash or a MIME::Type, the MIME::Type will be # constructed with #init_with. # * When provided an Array, the MIME::Type will be constructed using # the first element as the content type and the remaining flattened # elements as extensions. # * Otherwise, the content_type will be used as a string. # # Yields the newly constructed +self+ object. def initialize(content_type) # :yields self: @friendly = {} @obsolete = @registered = false @preferred_extension = @docs = @use_instead = nil self.extensions = [] case content_type when Hash init_with(content_type) when Array self.content_type = content_type.shift self.extensions = content_type.flatten when MIME::Type init_with(content_type.to_h) else self.content_type = content_type end self.encoding ||= :default self.xrefs ||= {} yield self if block_given? end # Indicates that a MIME type is like another type. This differs from # == because x- prefixes are removed for this comparison. def like?(other) other = if other.respond_to?(:simplified) MIME::Type.simplified(other.simplified, remove_x_prefix: true) else MIME::Type.simplified(other.to_s, remove_x_prefix: true) end MIME::Type.simplified(simplified, remove_x_prefix: true) == other end # Compares the +other+ MIME::Type against the exact content type or the # simplified type (the simplified type will be used if comparing against # something that can be treated as a String with #to_s). In comparisons, this # is done against the lowercase version of the MIME::Type. def <=>(other) if other.nil? -1 elsif other.respond_to?(:simplified) simplified <=> other.simplified else simplified <=> MIME::Type.simplified(other.to_s) end end # Compares the +other+ MIME::Type based on how reliable it is before doing a # normal <=> comparison. Used by MIME::Types#[] to sort types. The # comparisons involved are: # # 1. self.simplified <=> other.simplified (ensures that we # don't try to compare different types) # 2. IANA-registered definitions < other definitions. # 3. Complete definitions < incomplete definitions. # 4. Current definitions < obsolete definitions. # 5. Obselete with use-instead names < obsolete without. # 6. Obsolete use-instead definitions are compared. # # While this method is public, its use is strongly discouraged by consumers # of mime-types. In mime-types 3, this method is likely to see substantial # revision and simplification to ensure current registered content types sort # before unregistered or obsolete content types. def priority_compare(other) pc = simplified <=> other.simplified if pc.zero? pc = if (reg = registered?) != other.registered? reg ? -1 : 1 # registered < unregistered elsif (comp = complete?) != other.complete? comp ? -1 : 1 # complete < incomplete elsif (obs = obsolete?) != other.obsolete? obs ? 1 : -1 # current < obsolete elsif obs and ((ui = use_instead) != (oui = other.use_instead)) if ui.nil? 1 elsif oui.nil? -1 else ui <=> oui end else 0 end end pc end # Returns +true+ if the +other+ object is a MIME::Type and the content types # match. def eql?(other) other.kind_of?(MIME::Type) and self == other end # Returns the whole MIME content-type string. # # The content type is a presentation value from the MIME type registry and # should not be used for comparison. The case of the content type is # preserved, and extension markers (x-) are kept. # # text/plain => text/plain # x-chemical/x-pdb => x-chemical/x-pdb # audio/QCELP => audio/QCELP attr_reader :content_type # A simplified form of the MIME content-type string, suitable for # case-insensitive comparison, with any extension markers (x- text/plain # x-chemical/x-pdb => x-chemical/x-pdb # audio/QCELP => audio/qcelp attr_reader :simplified # Returns the media type of the simplified MIME::Type. # # text/plain => text # x-chemical/x-pdb => x-chemical # audio/QCELP => audio attr_reader :media_type # Returns the media type of the unmodified MIME::Type. # # text/plain => text # x-chemical/x-pdb => x-chemical # audio/QCELP => audio attr_reader :raw_media_type # Returns the sub-type of the simplified MIME::Type. # # text/plain => plain # x-chemical/x-pdb => pdb # audio/QCELP => QCELP attr_reader :sub_type # Returns the media type of the unmodified MIME::Type. # # text/plain => plain # x-chemical/x-pdb => x-pdb # audio/QCELP => qcelp attr_reader :raw_sub_type ## # The list of extensions which are known to be used for this MIME::Type. # Non-array values will be coerced into an array with #to_a. Array values # will be flattened, +nil+ values removed, and made unique. # # :attr_accessor: extensions def extensions @extensions.to_a end ## def extensions=(value) # :nodoc: @extensions = Set[*Array(value).flatten.compact].freeze MIME::Types.send(:reindex_extensions, self) end # Merge the +extensions+ provided into this MIME::Type. The extensions added # will be merged uniquely. def add_extensions(*extensions) self.extensions += extensions end ## # The preferred extension for this MIME type. If one is not set and there are # exceptions defined, the first extension will be used. # # When setting #preferred_extensions, if #extensions does not contain this # extension, this will be added to #xtensions. # # :attr_accessor: preferred_extension ## def preferred_extension @preferred_extension || extensions.first end ## def preferred_extension=(value) # :nodoc: add_extensions(value) if value @preferred_extension = value end ## # The encoding (+7bit+, +8bit+, quoted-printable, or +base64+) # required to transport the data of this content type safely across a # network, which roughly corresponds to Content-Transfer-Encoding. A value of # +nil+ or :default will reset the #encoding to the # #default_encoding for the MIME::Type. Raises ArgumentError if the encoding # provided is invalid. # # If the encoding is not provided on construction, this will be either # 'quoted-printable' (for text/* media types) and 'base64' for eveything # else. # # :attr_accessor: encoding ## attr_reader :encoding ## def encoding=(enc) # :nodoc: if enc.nil? or enc == :default @encoding = default_encoding elsif BINARY_ENCODINGS.include?(enc) or ASCII_ENCODINGS.include?(enc) @encoding = enc else fail InvalidEncoding, enc end end # Returns the default encoding for the MIME::Type based on the media type. def default_encoding (@media_type == 'text') ? 'quoted-printable' : 'base64' end ## # Returns the media type or types that should be used instead of this media # type, if it is obsolete. If there is no replacement media type, or it is # not obsolete, +nil+ will be returned. # # :attr_accessor: use_instead ## def use_instead obsolete? ? @use_instead : nil end ## attr_writer :use_instead # Returns +true+ if the media type is obsolete. attr_accessor :obsolete alias_method :obsolete?, :obsolete # The documentation for this MIME::Type. attr_accessor :docs # A friendly short description for this MIME::Type. # # call-seq: # text_plain.friendly # => "Text File" # text_plain.friendly('en') # => "Text File" def friendly(lang = 'en'.freeze) @friendly ||= {} case lang when String, Symbol @friendly[lang.to_s] when Array @friendly.update(Hash[*lang]) when Hash @friendly.update(lang) else fail ArgumentError, "Expected a language or translation set, not #{lang.inspect}" end end # A key suitable for use as a lookup key for translations, such as with # the I18n library. # # call-seq: # text_plain.i18n_key # => "text.plain" # 3gpp_xml.i18n_key # => "application.vnd-3gpp-bsf-xml" # # from application/vnd.3gpp.bsf+xml # x_msword.i18n_key # => "application.word" # # from application/x-msword attr_reader :i18n_key ## # The cross-references list for this MIME::Type. # # :attr_accessor: xrefs ## attr_reader :xrefs ## def xrefs=(x) # :nodoc: MIME::Types::Container.new.merge(x).tap do |xr| xr.each do |k, v| xr[k] = Set[*v] unless v.kind_of? Set end @xrefs = xr end end # The decoded cross-reference URL list for this MIME::Type. def xref_urls xrefs.flat_map { |type, values| name = :"xref_url_for_#{type.tr('-', '_')}" respond_to?(name, true) and xref_map(values, name) or values.to_a } end # Indicates whether the MIME type has been registered with IANA. attr_accessor :registered alias_method :registered?, :registered # MIME types can be specified to be sent across a network in particular # formats. This method returns +true+ when the MIME::Type encoding is set # to base64. def binary? BINARY_ENCODINGS.include?(encoding) end # MIME types can be specified to be sent across a network in particular # formats. This method returns +false+ when the MIME::Type encoding is # set to base64. def ascii? ASCII_ENCODINGS.include?(encoding) end # Indicateswhether the MIME type is declared as a signature type. attr_accessor :signature alias_method :signature?, :signature # Returns +true+ if the MIME::Type specifies an extension list, # indicating that it is a complete MIME::Type. def complete? !@extensions.empty? end # Returns the MIME::Type as a string. def to_s content_type end # Returns the MIME::Type as a string for implicit conversions. This allows # MIME::Type objects to appear on either side of a comparison. # # 'text/plain' == MIME::Type.new('text/plain') def to_str content_type end # Converts the MIME::Type to a JSON string. def to_json(*args) require 'json' to_h.to_json(*args) end # Converts the MIME::Type to a hash. The output of this method can also be # used to initialize a MIME::Type. def to_h encode_with({}) end # Populates the +coder+ with attributes about this record for # serialization. The structure of +coder+ should match the structure used # with #init_with. # # This method should be considered a private implementation detail. def encode_with(coder) coder['content-type'] = @content_type coder['docs'] = @docs unless @docs.nil? or @docs.empty? unless @friendly.nil? or @friendly.empty? coder['friendly'] = @friendly end coder['encoding'] = @encoding coder['extensions'] = @extensions.to_a unless @extensions.empty? coder['preferred-extension'] = @preferred_extension if @preferred_extension if obsolete? coder['obsolete'] = obsolete? coder['use-instead'] = use_instead if use_instead end unless xrefs.empty? {}.tap do |hash| xrefs.each do |k, v| hash[k] = v.sort.to_a end coder['xrefs'] = hash end end coder['registered'] = registered? coder['signature'] = signature? if signature? coder end # Initialize an empty object from +coder+, which must contain the # attributes necessary for initializing an empty object. # # This method should be considered a private implementation detail. def init_with(coder) self.content_type = coder['content-type'] self.docs = coder['docs'] || '' self.encoding = coder['encoding'] self.extensions = coder['extensions'] || [] self.preferred_extension = coder['preferred-extension'] self.obsolete = coder['obsolete'] || false self.registered = coder['registered'] || false self.signature = coder['signature'] self.xrefs = coder['xrefs'] || {} self.use_instead = coder['use-instead'] friendly(coder['friendly'] || {}) end def inspect # :nodoc: # We are intentionally lying here because MIME::Type::Columnar is an # implementation detail. "#" end class << self # MIME media types are case-insensitive, but are typically presented in a # case-preserving format in the type registry. This method converts # +content_type+ to lowercase. # # In previous versions of mime-types, this would also remove any extension # prefix (x-). This is no longer default behaviour, but may be # provided by providing a truth value to +remove_x_prefix+. def simplified(content_type, remove_x_prefix: false) simplify_matchdata(match(content_type), remove_x_prefix) end # Converts a provided +content_type+ into a translation key suitable for # use with the I18n library. def i18n_key(content_type) simplify_matchdata(match(content_type), joiner: '.') { |e| e.gsub!(I18N_RE, '-'.freeze) } end # Return a +MatchData+ object of the +content_type+ against pattern of # media types. def match(content_type) case content_type when MatchData content_type else MEDIA_TYPE_RE.match(content_type) end end private def simplify_matchdata(matchdata, remove_x = false, joiner: '/'.freeze) return nil unless matchdata matchdata.captures.map { |e| e.downcase! e.sub!(%r{^x-}, ''.freeze) if remove_x yield e if block_given? e }.join(joiner) end end private def content_type=(type_string) match = MEDIA_TYPE_RE.match(type_string) fail InvalidContentType, type_string if match.nil? @content_type = type_string @raw_media_type, @raw_sub_type = match.captures @simplified = MIME::Type.simplified(match) @i18n_key = MIME::Type.i18n_key(match) @media_type, @sub_type = MEDIA_TYPE_RE.match(@simplified).captures end def xref_map(values, helper) values.map { |value| send(helper, value) } end def xref_url_for_rfc(value) 'http://www.iana.org/go/%s'.freeze % value end def xref_url_for_draft(value) 'http://www.iana.org/go/%s'.freeze % value.sub(/\ARFC/, 'draft') end def xref_url_for_rfc_errata(value) 'http://www.rfc-editor.org/errata_search.php?eid=%s'.freeze % value end def xref_url_for_person(value) 'http://www.iana.org/assignments/media-types/media-types.xhtml#%s'.freeze % value end def xref_url_for_template(value) 'http://www.iana.org/assignments/media-types/%s'.freeze % value end end mime-types-3.1/test/0000755000004100000410000000000012722123747014464 5ustar www-datawww-datamime-types-3.1/test/test_mime_types_cache.rb0000644000004100000410000000573112722123747021354 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Types::Cache do include Minitest::Hooks MUTEX = Mutex.new def around require 'fileutils' MUTEX.synchronize do @cache_file = File.expand_path('../cache.tst', __FILE__) ENV['RUBY_MIME_TYPES_CACHE'] = @cache_file clear_cache_file super clear_cache_file ENV.delete('RUBY_MIME_TYPES_CACHE') end end def reset_mime_types MIME::Types.instance_variable_set(:@__types__, nil) MIME::Types.send(:load_default_mime_types) end def clear_cache_file FileUtils.rm @cache_file if File.exist? @cache_file end describe '.load' do it 'does not use cache when RUBY_MIME_TYPES_CACHE is unset' do ENV.delete('RUBY_MIME_TYPES_CACHE') assert_equal(nil, MIME::Types::Cache.load) end it 'does not use cache when missing' do assert_equal(nil, MIME::Types::Cache.load) end it 'outputs an error when there is an invalid version' do v = MIME::Types::Data::VERSION MIME::Types::Data.send(:remove_const, :VERSION) MIME::Types::Data.const_set(:VERSION, '0.0') MIME::Types::Cache.save MIME::Types::Data.send(:remove_const, :VERSION) MIME::Types::Data.const_set(:VERSION, v) MIME::Types.instance_variable_set(:@__types__, nil) assert_output '', /MIME::Types cache: invalid version/ do MIME::Types['text/html'] end end it 'outputs an error when there is a marshal file incompatibility' do MIME::Types::Cache.save data = File.binread(@cache_file).reverse File.open(@cache_file, 'wb') { |f| f.write(data) } MIME::Types.instance_variable_set(:@__types__, nil) assert_output '', /incompatible marshal file format/ do MIME::Types['text/html'] end end end describe '.save' do it 'does not create cache when RUBY_MIME_TYPES_CACHE is unset' do ENV.delete('RUBY_MIME_TYPES_CACHE') assert_equal(nil, MIME::Types::Cache.save) end it 'creates the cache ' do assert_equal(false, File.exist?(@cache_file)) MIME::Types::Cache.save assert_equal(true, File.exist?(@cache_file)) end it 'uses the cache' do MIME::Types['text/html'].first.add_extensions('hex') MIME::Types::Cache.save MIME::Types.instance_variable_set(:@__types__, nil) assert_includes MIME::Types['text/html'].first.extensions, 'hex' reset_mime_types end end end describe MIME::Types::Container do it 'marshals and unmarshals correctly' do container = MIME::Types::Container.new container['xyz'] << 'abc' # default proc should return Set[] assert_equal(Set[], container['abc']) assert_equal(Set['abc'], container['xyz']) marshalled = Marshal.dump(container) loaded_container = Marshal.load(marshalled) # default proc should still return Set[] assert_equal(Set[], loaded_container['abc']) assert_equal(Set['abc'], container['xyz']) end end mime-types-3.1/test/fixture/0000755000004100000410000000000012722123747016152 5ustar www-datawww-datamime-types-3.1/test/fixture/old-data0000644000004100000410000000074412722123747017567 0ustar www-datawww-data!application/smil @smi,smil :8bit 'IANA,RFC4536 =use-instead:application/smil+xml !audio/vnd.qcelp @qcp 'IANA,RFC3625 =use-instead:audio/QCELP *!image/bmp @bmp =use-instead:image/x-bmp *application/acad 'LTSW *audio/webm @webm '{WebM=http://www.webmproject.org/code/specs/container/} *image/pjpeg :base64 =Fixes a bug with IE6 and progressive JPEGs application/1d-interleaved-parityfec 'IANA,RFC6015 audio/1d-interleaved-parityfec 'IANA,RFC6015 mac:application/x-apple-diskimage @dmg mime-types-3.1/test/fixture/json.json0000644000004100000410000000175512722123747020026 0ustar www-datawww-data[{"content-type":"application/smil","encoding":"8bit","extensions":["smi","smil"],"obsolete":true,"use-instead":"application/smil+xml","registered":true},{"content-type":"audio/vnd.qcelp","encoding":"base64","extensions":["qcp"],"obsolete":true,"use-instead":"audio/QCELP","registered":true},{"content-type":"image/bmp","encoding":"base64","extensions":["bmp"],"obsolete":true,"use-instead":"image/x-bmp","registered":false},{"content-type":"application/acad","encoding":"base64","registered":false},{"content-type":"audio/webm","encoding":"base64","extensions":["webm"],"registered":false},{"content-type":"image/pjpeg","docs":"Fixes a bug with IE6 and progressive JPEGs","encoding":"base64","registered":false},{"content-type":"application/1d-interleaved-parityfec","encoding":"base64","registered":true},{"content-type":"audio/1d-interleaved-parityfec","encoding":"base64","registered":true},{"content-type":"application/x-apple-diskimage","encoding":"base64","extensions":["dmg"],"registered":false}] mime-types-3.1/test/fixture/yaml.yaml0000644000004100000410000000230412722123747017777 0ustar www-datawww-data--- - !ruby/object:MIME::Type content-type: application/smil encoding: 8bit extensions: - smi - smil obsolete: true use-instead: application/smil+xml registered: true - !ruby/object:MIME::Type content-type: audio/vnd.qcelp encoding: base64 extensions: - qcp obsolete: true use-instead: audio/QCELP registered: true - !ruby/object:MIME::Type content-type: image/bmp encoding: base64 extensions: - bmp obsolete: true use-instead: image/x-bmp registered: false - !ruby/object:MIME::Type content-type: application/acad encoding: base64 registered: false - !ruby/object:MIME::Type content-type: audio/webm encoding: base64 extensions: - webm registered: false - !ruby/object:MIME::Type content-type: image/pjpeg docs: Fixes a bug with IE6 and progressive JPEGs encoding: base64 registered: false - !ruby/object:MIME::Type content-type: application/1d-interleaved-parityfec encoding: base64 registered: true - !ruby/object:MIME::Type content-type: audio/1d-interleaved-parityfec encoding: base64 registered: true - !ruby/object:MIME::Type content-type: application/x-apple-diskimage encoding: base64 extensions: - dmg registered: false mime-types-3.1/test/test_mime_type.rb0000644000004100000410000004174012722123747020046 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Type do # it { fail } def mime_type(content_type) MIME::Type.new(content_type) { |mt| yield mt if block_given? } end let(:x_appl_x_zip) { mime_type('x-appl/x-zip') { |t| t.extensions = %w(zip zp) } } let(:text_plain) { mime_type('text/plain') } let(:text_html) { mime_type('text/html') } let(:image_jpeg) { mime_type('image/jpeg') } let(:application_javascript) { mime_type('application/javascript') do |js| js.friendly('en' => 'JavaScript') js.xrefs = { 'rfc' => %w(rfc4239 rfc4239), 'template' => %w(application/javascript) } js.encoding = '8bit' js.extensions = %w(js sj) js.registered = true end } let(:text_x_yaml) { mime_type('text/x-yaml') do |yaml| yaml.extensions = %w(yaml yml) yaml.encoding = '8bit' yaml.friendly('en' => 'YAML Structured Document') end } let(:text_x_yaml_with_docs) { text_x_yaml.dup.tap do |yaml| yaml.docs = 'Test YAML' end } describe '.simplified' do it 'leaves normal types alone' do assert_equal 'text/plain', MIME::Type.simplified('text/plain') end it 'does not remove x- prefixes by default' do assert_equal 'application/x-msword', MIME::Type.simplified('application/x-msword') assert_equal 'x-xyz/abc', MIME::Type.simplified('x-xyz/abc') end it 'removes x- prefixes when requested' do assert_equal 'application/msword', MIME::Type.simplified('application/x-msword', remove_x_prefix: true) assert_equal 'xyz/abc', MIME::Type.simplified('x-xyz/abc', remove_x_prefix: true) end it 'lowercases mixed-case types' do assert_equal 'text/vcard', MIME::Type.simplified('text/vCard') end it 'returns nil when the value provided is not a valid content type' do assert_nil MIME::Type.simplified('text') end end describe '.i18n_key' do it 'converts text/plain to text.plain' do assert_equal 'text.plain', MIME::Type.i18n_key('text/plain') end it 'does not remove x-prefixes' do assert_equal 'application.x-msword', MIME::Type.i18n_key('application/x-msword') end it 'converts text/vCard to text.vcard' do assert_equal 'text.vcard', MIME::Type.i18n_key('text/vCard') end it 'returns nil when the value provided is not a valid content type' do assert_nil MIME::Type.i18n_key('text') end end describe '.new' do it 'fails if an invalid content type is provided' do exception = assert_raises MIME::Type::InvalidContentType do MIME::Type.new('apps') end assert_equal 'Invalid Content-Type "apps"', exception.to_s end it 'creates a valid content type just from a string' do type = MIME::Type.new('text/x-yaml') assert_instance_of MIME::Type, type assert_equal 'text/x-yaml', type.content_type end it 'yields the content type in a block' do MIME::Type.new('text/x-yaml') do |type| assert_instance_of MIME::Type, type assert_equal 'text/x-yaml', type.content_type end end it 'creates a valid content type from a hash' do type = MIME::Type.new( 'content-type' => 'text/x-yaml', 'obsolete' => true ) assert_instance_of MIME::Type, type assert_equal 'text/x-yaml', type.content_type assert type.obsolete? end it 'creates a valid content type from an array' do type = MIME::Type.new(%w(text/x-yaml yaml yml yz)) assert_instance_of MIME::Type, type assert_equal 'text/x-yaml', type.content_type assert_equal %w(yaml yml yz), type.extensions end end describe '#like?' do it 'compares two MIME::Types on #simplified values without x- prefixes' do assert text_plain.like?(text_plain) refute text_plain.like?(text_html) end it 'compares MIME::Type against string without x- prefixes' do assert text_plain.like?(text_plain.to_s) refute text_plain.like?(text_html.to_s) end end describe '#<=>' do it 'correctly compares identical types' do assert_equal text_plain, text_plain end it 'correctly compares equivalent types' do right = mime_type('text/Plain') refute_same text_plain, right assert_equal text_plain, right end it 'correctly compares types that sort earlier' do refute_equal text_html, text_plain assert_operator text_html, :<, text_plain end it 'correctly compares types that sort later' do refute_equal text_plain, text_html assert_operator text_plain, :>, text_html end it 'correctly compares types against equivalent strings' do assert_equal text_plain, 'text/plain' end it 'correctly compares types against strings that sort earlier' do refute_equal text_html, 'text/plain' assert_operator text_html, :<, 'text/plain' end it 'correctly compares types against strings that sort later' do refute_equal text_plain, 'text/html' assert_operator text_plain, :>, 'text/html' end it 'correctly compares against nil' do refute_equal text_html, nil assert_operator text_plain, :<, nil end end describe '#ascii?' do it 'defaults to true for text/* types' do assert text_plain.ascii? end it 'defaults to false for non-text/* types' do refute image_jpeg.ascii? end end describe '#binary?' do it 'defaults to false for text/* types' do refute text_plain.binary? end it 'defaults to true for non-text/* types' do assert image_jpeg.binary? end end describe '#complete?' do it 'is true when there are extensions' do assert text_x_yaml.complete? end it 'is false when there are no extensions' do refute mime_type('text/plain').complete? end end describe '#content_type' do it 'preserves the original case' do assert_equal 'text/plain', text_plain.content_type assert_equal 'text/vCard', mime_type('text/vCard').content_type end it 'does not remove x- prefixes' do assert_equal 'x-appl/x-zip', x_appl_x_zip.content_type end end describe '#default_encoding' do it 'is quoted-printable for text/* types' do assert_equal 'quoted-printable', text_plain.default_encoding end it 'is base64 for non-text/* types' do assert_equal 'base64', image_jpeg.default_encoding end end describe '#encoding, #encoding=' do it 'returns #default_encoding if not set explicitly' do assert_equal 'quoted-printable', text_plain.encoding assert_equal 'base64', image_jpeg.encoding end it 'returns the set value when set' do text_plain.encoding = '8bit' assert_equal '8bit', text_plain.encoding end it 'resets to the default encoding when set to nil or :default' do text_plain.encoding = '8bit' text_plain.encoding = nil assert_equal text_plain.default_encoding, text_plain.encoding text_plain.encoding = :default assert_equal text_plain.default_encoding, text_plain.encoding end it 'raises a MIME::Type::InvalidEncoding for an invalid encoding' do exception = assert_raises MIME::Type::InvalidEncoding do text_plain.encoding = 'binary' end assert_equal 'Invalid Encoding "binary"', exception.to_s end end describe '#eql?' do it 'is not true for a non-MIME::Type' do refute text_plain.eql?('text/plain') end it 'is not true for a different MIME::Type' do refute text_plain.eql?(image_jpeg) end it 'is true for an equivalent MIME::Type' do assert text_plain, mime_type('text/Plain') end end describe '#extensions, #extensions=' do it 'returns an array of extensions' do assert_equal %w(yaml yml), text_x_yaml.extensions assert_equal %w(zip zp), x_appl_x_zip.extensions end it 'sets a single extension when provided a single value' do text_x_yaml.extensions = 'yaml' assert_equal %w(yaml), text_x_yaml.extensions end it 'deduplicates extensions' do text_x_yaml.extensions = %w(yaml yaml) assert_equal %w(yaml), text_x_yaml.extensions end end describe '#add_extensions' do it 'does not modify extensions when provided nil' do text_x_yaml.add_extensions(nil) assert_equal %w(yaml yml), text_x_yaml.extensions end it 'remains deduplicated with duplicate values' do text_x_yaml.add_extensions('yaml') assert_equal %w(yaml yml), text_x_yaml.extensions text_x_yaml.add_extensions(%w(yaml yz)) assert_equal %w(yaml yml yz), text_x_yaml.extensions end end describe '#priority_compare' do def assert_priority_less(left, right) assert_equal(-1, left.priority_compare(right)) end def assert_priority_same(left, right) assert_equal 0, left.priority_compare(right) end def assert_priority_more(left, right) assert_equal 1, left.priority_compare(right) end def assert_priority(left, middle, right) assert_priority_less left, right assert_priority_same left, middle assert_priority_more right, left end let(:text_1) { mime_type('text/1') } let(:text_1p) { mime_type('text/1') } let(:text_2) { mime_type('text/2') } it 'sorts (1) based on the simplified type' do assert_priority text_1, text_1p, text_2 end it 'sorts (2) based on the registration state' do text_1.registered = text_1p.registered = true text_1b = mime_type(text_1) { |t| t.registered = false } assert_priority text_1, text_1p, text_1b end it 'sorts (3) based on the completeness' do text_1.extensions = text_1p.extensions = '1' text_1b = mime_type(text_1) { |t| t.extensions = nil } assert_priority text_1, text_1p, text_1b end it 'sorts (4) based on obsolete status' do text_1.obsolete = text_1p.obsolete = false text_1b = mime_type(text_1) { |t| t.obsolete = true } assert_priority text_1, text_1p, text_1b end it 'sorts (5) based on the use-instead value' do text_1.obsolete = text_1p.obsolete = true text_1.use_instead = text_1p.use_instead = 'abc/xyz' text_1b = mime_type(text_1) { |t| t.use_instead = nil } assert_priority text_1, text_1p, text_1b text_1b.use_instead = 'abc/zzz' assert_priority text_1, text_1p, text_1b end end describe '#raw_media_type' do it 'extracts the media type as case-preserved' do assert_equal 'Text', mime_type('Text/plain').raw_media_type end it 'does not remove x- prefixes' do assert_equal('x-appl', x_appl_x_zip.raw_media_type) end end describe '#media_type' do it 'extracts the media type as lowercase' do assert_equal 'text', text_plain.media_type end it 'does not remove x- prefixes' do assert_equal('x-appl', x_appl_x_zip.media_type) end end describe '#raw_media_type' do it 'extracts the media type as case-preserved' do assert_equal 'Text', mime_type('Text/plain').raw_media_type end it 'does not remove x- prefixes' do assert_equal('x-appl', x_appl_x_zip.raw_media_type) end end describe '#sub_type' do it 'extracts the sub type as lowercase' do assert_equal 'plain', text_plain.sub_type end it 'does not remove x- prefixes' do assert_equal('x-zip', x_appl_x_zip.sub_type) end end describe '#raw_sub_type' do it 'extracts the sub type as case-preserved' do assert_equal 'Plain', mime_type('text/Plain').raw_sub_type end it 'does not remove x- prefixes' do assert_equal('x-zip', x_appl_x_zip.raw_sub_type) end end describe '#to_h' do let(:t) { mime_type('a/b') } it 'has the required keys (content-type, registered, encoding)' do assert_has_keys t.to_h, %w(content-type registered encoding) end it 'has the docs key if there are documents' do assert_has_keys mime_type(t) { |v| v.docs = 'a' }.to_h, %w(docs) end it 'has the extensions key if set' do assert_has_keys mime_type(t) { |v| v.extensions = 'a' }.to_h, 'extensions' end it 'has the preferred-extension key if set' do assert_has_keys mime_type(t) { |v| v.preferred_extension = 'a' }.to_h, 'preferred-extension' end it 'has the obsolete key if set' do assert_has_keys mime_type(t) { |v| v.obsolete = true }.to_h, 'obsolete' end it 'has the obsolete and use-instead keys if set' do assert_has_keys mime_type(t) { |v| v.obsolete = true v.use_instead = 'c/d' }.to_h, %w(obsolete use-instead) end it 'has the signature key if set' do assert_has_keys mime_type(t) { |v| v.signature = true }.to_h, 'signature' end end describe '#to_json' do let(:expected) { '{"content-type":"a/b","encoding":"base64","registered":false}' } it 'converts to JSON when requested' do assert_equal expected, mime_type('a/b').to_json end end describe '#to_s, #to_str' do it 'represents itself as a string of the canonical content_type' do assert_equal 'text/plain', "#{text_plain}" end it 'acts like a string of the canonical content_type for comparison' do assert_equal text_plain, 'text/plain' end it 'acts like a string for other purposes' do assert_equal 'stringy', 'text/plain'.sub(text_plain, 'stringy') end end describe '#xrefs, #xrefs=' do let(:expected) { { 'rfc' => Set[*%w(rfc1234 rfc5678)] } } it 'returns the expected results' do application_javascript.xrefs = { 'rfc' => %w(rfc5678 rfc1234 rfc1234) } assert_equal expected, application_javascript.xrefs end end describe '#xref_urls' do let(:expected) { [ 'http://www.iana.org/go/draft1', 'http://www.iana.org/assignments/media-types/a/b', 'http://www.iana.org/assignments/media-types/media-types.xhtml#p-1', 'http://www.iana.org/go/rfc-1', 'http://www.rfc-editor.org/errata_search.php?eid=err-1', 'http://example.org', 'text' ] } let(:type) { mime_type('a/b').tap do |t| t.xrefs = { 'draft' => [ 'RFC1' ], 'template' => [ 'a/b' ], 'person' => [ 'p-1' ], 'rfc' => [ 'rfc-1' ], 'rfc-errata' => [ 'err-1' ], 'uri' => [ 'http://example.org' ], 'text' => [ 'text' ] } end } it 'translates according to given rules' do assert_equal expected, type.xref_urls end end describe '#use_instead' do it 'is nil unless the type is obsolete' do assert_nil text_plain.use_instead end it 'is nil if not set and the type is obsolete' do text_plain.obsolete = true assert_nil text_plain.use_instead end it 'is a different type if set and the type is obsolete' do text_plain.obsolete = true text_plain.use_instead = 'text/html' assert_equal 'text/html', text_plain.use_instead end end describe '#preferred_extension, #preferred_extension=' do it 'is nil when not set and there are no extensions' do assert_nil text_plain.preferred_extension end it 'is the first extension when not set but there are extensions' do assert_equal 'yaml', text_x_yaml.preferred_extension end it 'is the extension provided when set' do text_x_yaml.preferred_extension = 'yml' assert_equal 'yml', text_x_yaml.preferred_extension end it 'is adds the preferred extension if it does not exist' do text_x_yaml.preferred_extension = 'yz' assert_equal 'yz', text_x_yaml.preferred_extension assert_includes text_x_yaml.extensions, 'yz' end end describe '#friendly' do it 'returns English by default' do assert_equal 'YAML Structured Document', text_x_yaml.friendly end it 'returns English when requested' do assert_equal 'YAML Structured Document', text_x_yaml.friendly('en') assert_equal 'YAML Structured Document', text_x_yaml.friendly(:en) end it 'returns nothing for an unknown language' do assert_nil text_x_yaml.friendly('zz') end it 'merges new values from an array parameter' do expected = { 'en' => 'Text files' } assert_equal expected, text_plain.friendly([ 'en', 'Text files' ]) expected.update('fr' => 'des fichiers texte') assert_equal expected, text_plain.friendly([ 'fr', 'des fichiers texte' ]) end it 'merges new values from a hash parameter' do expected = { 'en' => 'Text files' } assert_equal expected, text_plain.friendly(expected) french = { 'fr' => 'des fichiers texte' } expected.update(french) assert_equal expected, text_plain.friendly(french) end it 'raises an ArgumentError if an unknown value is provided' do exception = assert_raises ArgumentError do text_plain.friendly(1) end assert_equal 'Expected a language or translation set, not 1', exception.message end end end mime-types-3.1/test/bad-fixtures/0000755000004100000410000000000012722123747017061 5ustar www-datawww-datamime-types-3.1/test/bad-fixtures/malformed0000644000004100000410000000074412722123747020757 0ustar www-datawww-data!application.smil @smi,smil :8bit 'IANA,RFC4536 =use-instead:application/smil+xml !audio/vnd.qcelp @qcp 'IANA,RFC3625 =use-instead:audio/QCELP *!image/bmp @bmp =use-instead:image/x-bmp *application/acad 'LTSW *audio/webm @webm '{WebM=http://www.webmproject.org/code/specs/container/} *image/pjpeg :base64 =Fixes a bug with IE6 and progressive JPEGs application/1d-interleaved-parityfec 'IANA,RFC6015 audio/1d-interleaved-parityfec 'IANA,RFC6015 mac:application/x-apple-diskimage @dmg mime-types-3.1/test/test_mime_types.rb0000644000004100000410000001155512722123747020232 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Types do def mime_types @mime_types ||= MIME::Types.new.tap do |mt| mt.add MIME::Type.new(['text/plain', %w(txt)]), MIME::Type.new(['image/jpeg', %w(jpg jpeg)]), MIME::Type.new('application/x-wordperfect6.1'), MIME::Type.new( 'content-type' => 'application/x-www-form-urlencoded', 'registered' => true ), MIME::Type.new(['application/x-gzip', %w(gz)]), MIME::Type.new( 'content-type' => 'application/gzip', 'extensions' => 'gz', 'registered' => true ) end end describe 'is enumerable' do it 'correctly uses an Enumerable method like #any?' do assert mime_types.any? { |type| type.content_type == 'text/plain' } end it 'implements each with no parameters to return an Enumerator' do assert_kind_of Enumerator, mime_types.each assert_kind_of Enumerator, mime_types.map end it 'will create a lazy enumerator' do assert_kind_of Enumerator::Lazy, mime_types.lazy assert_kind_of Enumerator::Lazy, mime_types.map.lazy end it 'is countable with an enumerator' do assert_equal 6, mime_types.each.count assert_equal 6, mime_types.lazy.count end end describe '#[]' do it 'can be searched with a MIME::Type' do text_plain = MIME::Type.new('text/plain') assert_includes mime_types[text_plain], 'text/plain' assert_equal 1, mime_types[text_plain].size end it 'can be searched with a regular expression' do assert_includes mime_types[/plain$/], 'text/plain' assert_equal 1, mime_types[/plain$/].size end it 'sorts by priority with multiple matches' do assert_equal %w(application/gzip application/x-gzip), mime_types[/gzip$/] assert_equal 2, mime_types[/gzip$/].size end it 'can be searched with a string' do assert_includes mime_types['text/plain'], 'text/plain' assert_equal 1, mime_types['text/plain'].size end it 'can be searched with the complete flag' do assert_empty mime_types[ 'application/x-www-form-urlencoded', complete: true ] assert_includes mime_types['text/plain', complete: true], 'text/plain' assert_equal 1, mime_types['text/plain', complete: true].size end it 'can be searched with the registered flag' do assert_empty mime_types['application/x-wordperfect6.1', registered: true] refute_empty mime_types[ 'application/x-www-form-urlencoded', registered: true ] refute_empty mime_types[/gzip/, registered: true] refute_equal mime_types[/gzip/], mime_types[/gzip/, registered: true] end end describe '#add' do let(:eruby) { MIME::Type.new('application/x-eruby') } let(:jinja) { MIME::Type.new('application/jinja2' )} it 'successfully adds a new type' do mime_types.add(eruby) assert_equal mime_types['application/x-eruby'], [ eruby ] end it 'complains about adding a duplicate type' do mime_types.add(eruby) assert_output '', /is already registered as a variant/ do mime_types.add(eruby) end assert_equal mime_types['application/x-eruby'], [eruby] end it 'does not complain about adding a duplicate type when quiet' do mime_types.add(eruby) assert_output '', '' do mime_types.add(eruby, :silent) end assert_equal mime_types['application/x-eruby'], [ eruby ] end it 'successfully adds from an array' do mime_types.add([ eruby, jinja ]) assert_equal mime_types['application/x-eruby'], [ eruby ] assert_equal mime_types['application/jinja2'], [ jinja ] end it 'successfully adds from another MIME::Types' do mt = MIME::Types.new mt.add(mime_types) assert_equal mime_types.count, mt.count mime_types.each do |type| assert_equal mt[type.content_type], [ type ] end end end describe '#type_for' do it 'finds all types for a given extension' do assert_equal %w(application/gzip application/x-gzip), mime_types.type_for('gz') end it 'separates the extension from filenames' do assert_equal %w(image/jpeg), mime_types.of(['foo.jpeg', 'bar.jpeg']) end it 'finds multiple extensions' do assert_equal %w(image/jpeg text/plain), mime_types.type_for(%w(foo.txt foo.jpeg)) end it 'does not find unknown extensions' do assert_empty mime_types.type_for('zzz') end it 'modifying type extensions causes reindexing' do plain_text = mime_types['text/plain'].first plain_text.add_extensions('xtxt') assert_includes mime_types.type_for('xtxt'), 'text/plain' end end describe '#count' do it 'can count the number of types inside' do assert_equal 6, mime_types.count end end end mime-types-3.1/test/minitest_helper.rb0000644000004100000410000000042112722123747020201 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/type' require 'fileutils' gem 'minitest' require 'fivemat/minitest/autorun' require 'minitest/focus' require 'minitest/rg' require 'minitest-bonus-assertions' require 'minitest/hooks' ENV['RUBY_MIME_TYPES_LAZY_LOAD'] = 'yes' mime-types-3.1/test/test_mime_types_lazy.rb0000644000004100000410000000226012722123747021262 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Types, 'lazy loading' do def setup ENV['RUBY_MIME_TYPES_LAZY_LOAD'] = 'true' end def teardown reset_mime_types ENV.delete('RUBY_MIME_TYPES_LAZY_LOAD') end def reset_mime_types MIME::Types.instance_variable_set(:@__types__, nil) MIME::Types.send(:load_default_mime_types) end describe '.lazy_load?' do it 'is true when RUBY_MIME_TYPES_LAZY_LOAD is set' do assert_equal true, MIME::Types.send(:lazy_load?) end it 'is nil when RUBY_MIME_TYPES_LAZY_LOAD is unset' do ENV['RUBY_MIME_TYPES_LAZY_LOAD'] = nil assert_equal nil, MIME::Types.send(:lazy_load?) end it 'is false when RUBY_MIME_TYPES_LAZY_LOAD is false' do ENV['RUBY_MIME_TYPES_LAZY_LOAD'] = 'false' assert_equal false, MIME::Types.send(:lazy_load?) end end it 'loads lazily when RUBY_MIME_TYPES_LAZY_LOAD is set' do MIME::Types.instance_variable_set(:@__types__, nil) assert_nil MIME::Types.instance_variable_get(:@__types__) refute_nil MIME::Types['text/html'].first refute_nil MIME::Types.instance_variable_get(:@__types__) end end mime-types-3.1/test/test_mime_types_class.rb0000644000004100000410000001111712722123747021411 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Types, 'registry' do def setup MIME::Types.send(:load_default_mime_types) end describe 'is enumerable' do it 'correctly uses an Enumerable method like #any?' do assert MIME::Types.any? { |type| type.content_type == 'text/plain' } end it 'implements each with no parameters to return an Enumerator' do assert_kind_of Enumerator, MIME::Types.each assert_kind_of Enumerator, MIME::Types.map end it 'will create a lazy enumerator' do assert_kind_of Enumerator::Lazy, MIME::Types.lazy assert_kind_of Enumerator::Lazy, MIME::Types.map.lazy end it 'is countable with an enumerator' do assert MIME::Types.each.count > 999 assert MIME::Types.lazy.count > 999 end end describe '.[]' do it 'can be searched with a MIME::Type' do text_plain = MIME::Type.new('text/plain') assert_includes MIME::Types[text_plain], 'text/plain' assert_equal 1, MIME::Types[text_plain].size end it 'can be searched with a regular expression' do assert_includes MIME::Types[/plain$/], 'text/plain' assert_equal 1, MIME::Types[/plain$/].size end it 'sorts by priority with multiple matches' do assert_equal %w(application/gzip application/x-gzip multipart/x-gzip), MIME::Types[/gzip$/] assert_equal 3, MIME::Types[/gzip$/].size end it 'can be searched with a string' do assert_includes MIME::Types['text/plain'], 'text/plain' assert_equal 1, MIME::Types['text/plain'].size end it 'can be searched with the complete flag' do assert_empty MIME::Types[ 'application/x-www-form-urlencoded', complete: true ] assert_includes MIME::Types['text/plain', complete: true], 'text/plain' assert_equal 1, MIME::Types['text/plain', complete: true].size end it 'can be searched with the registered flag' do assert_empty MIME::Types['application/x-wordperfect6.1', registered: true] refute_empty MIME::Types[ 'application/x-www-form-urlencoded', registered: true ] refute_empty MIME::Types[/gzip/, registered: true] refute_equal MIME::Types[/gzip/], MIME::Types[/gzip/, registered: true] end end describe '.type_for' do it 'finds all types for a given extension' do assert_equal %w(application/gzip application/x-gzip), MIME::Types.type_for('gz') end it 'separates the extension from filenames' do assert_equal %w(image/jpeg), MIME::Types.of(['foo.jpeg', 'bar.jpeg']) end it 'finds multiple extensions' do assert_equal %w(image/jpeg text/plain), MIME::Types.type_for(%w(foo.txt foo.jpeg)) end it 'does not find unknown extensions' do assert_empty MIME::Types.type_for('zzz') end it 'modifying type extensions causes reindexing' do plain_text = MIME::Types['text/plain'].first plain_text.add_extensions('xtxt') assert_includes MIME::Types.type_for('xtxt'), 'text/plain' end end describe '.count' do it 'can count the number of types inside' do assert MIME::Types.count > 999 end end describe '.add' do def setup MIME::Types.instance_variable_set(:@__types__, nil) MIME::Types.send(:load_default_mime_types) end let(:eruby) { MIME::Type.new('application/x-eruby') } let(:jinja) { MIME::Type.new('application/jinja2' )} it 'successfully adds a new type' do MIME::Types.add(eruby) assert_equal MIME::Types['application/x-eruby'], [ eruby ] end it 'complains about adding a duplicate type' do MIME::Types.add(eruby) assert_output '', /is already registered as a variant/ do MIME::Types.add(eruby) end assert_equal MIME::Types['application/x-eruby'], [eruby] end it 'does not complain about adding a duplicate type when quiet' do MIME::Types.add(eruby) assert_silent do MIME::Types.add(eruby, :silent) end assert_equal MIME::Types['application/x-eruby'], [ eruby ] end it 'successfully adds from an array' do MIME::Types.add([ eruby, jinja ]) assert_equal MIME::Types['application/x-eruby'], [ eruby ] assert_equal MIME::Types['application/jinja2'], [ jinja ] end it 'successfully adds from another MIME::Types' do old_count = MIME::Types.count mt = MIME::Types.new mt.add(eruby) MIME::Types.add(mt) assert_equal old_count + 1, MIME::Types.count assert_equal MIME::Types[eruby.content_type], [ eruby ] end end end mime-types-3.1/test/test_mime_types_loader.rb0000644000004100000410000000166612722123747021562 0ustar www-datawww-data# -*- ruby encoding: utf-8 -*- require 'mime/types' require 'minitest_helper' describe MIME::Types::Loader do def setup @path = File.expand_path('../fixture', __FILE__) @loader = MIME::Types::Loader.new(@path) @bad_path = File.expand_path('../bad-fixtures', __FILE__) end def assert_correctly_loaded(types) assert_includes(types, 'application/1d-interleaved-parityfec') assert_equal(%w(webm), types['audio/webm'].first.extensions) refute(types['audio/webm'].first.registered?) assert_equal('Fixes a bug with IE6 and progressive JPEGs', types['image/pjpeg'].first.docs) assert(types['audio/vnd.qcelp'].first.obsolete?) assert_equal('audio/QCELP', types['audio/vnd.qcelp'].first.use_instead) end it 'loads YAML files correctly' do assert_correctly_loaded @loader.load_yaml end it 'loads JSON files correctly' do assert_correctly_loaded @loader.load_json end end mime-types-3.1/mime-types.gemspec0000644000004100000410000001273012722123750017140 0ustar www-datawww-data######################################################### # This file has been automatically generated by gem2tgz # ######################################################### # -*- encoding: utf-8 -*- Gem::Specification.new do |s| s.name = "mime-types" s.version = "3.1" s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version= s.authors = ["Austin Ziegler"] s.date = "2016-05-22" s.description = "The mime-types library provides a library and registry for information about\nMIME content type definitions. It can be used to determine defined filename\nextensions for MIME types, or to use filename extensions to look up the likely\nMIME type definitions.\n\nVersion 3.0 is a major release that requires Ruby 2.0 compatibility and removes\ndeprecated functions. The columnar registry format introduced in 2.6 has been\nmade the primary format; the registry data has been extracted from this library\nand put into {mime-types-data}[https://github.com/mime-types/mime-types-data].\nAdditionally, mime-types is now licensed exclusively under the MIT licence and\nthere is a code of conduct in effect. There are a number of other smaller\nchanges described in the History file." s.email = ["halostatue@gmail.com"] s.extra_rdoc_files = ["Code-of-Conduct.rdoc", "Contributing.rdoc", "History.rdoc", "Licence.rdoc", "Manifest.txt", "README.rdoc"] s.files = ["Code-of-Conduct.rdoc", "Contributing.rdoc", "History.rdoc", "Licence.rdoc", "Manifest.txt", "README.rdoc", "Rakefile", "lib/mime-types.rb", "lib/mime/type.rb", "lib/mime/type/columnar.rb", "lib/mime/types.rb", "lib/mime/types/_columnar.rb", "lib/mime/types/cache.rb", "lib/mime/types/columnar.rb", "lib/mime/types/container.rb", "lib/mime/types/deprecations.rb", "lib/mime/types/full.rb", "lib/mime/types/loader.rb", "lib/mime/types/logger.rb", "lib/mime/types/registry.rb", "test/bad-fixtures/malformed", "test/fixture/json.json", "test/fixture/old-data", "test/fixture/yaml.yaml", "test/minitest_helper.rb", "test/test_mime_type.rb", "test/test_mime_types.rb", "test/test_mime_types_cache.rb", "test/test_mime_types_class.rb", "test/test_mime_types_lazy.rb", "test/test_mime_types_loader.rb"] s.homepage = "https://github.com/mime-types/ruby-mime-types/" s.licenses = ["MIT"] s.rdoc_options = ["--main", "README.rdoc"] s.require_paths = ["lib"] s.required_ruby_version = Gem::Requirement.new(">= 2.0") s.rubygems_version = "1.8.23" s.summary = "The mime-types library provides a library and registry for information about MIME content type definitions" if s.respond_to? :specification_version then s.specification_version = 4 if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then s.add_development_dependency(%q, ["~> 1.3"]) s.add_development_dependency(%q, ["~> 3.15"]) s.add_development_dependency(%q, ["~> 1.0"]) s.add_development_dependency(%q, ["~> 1.1"]) s.add_development_dependency(%q, ["~> 1.6"]) s.add_development_dependency(%q, ["~> 1.0"]) s.add_development_dependency(%q, ["~> 1.2"]) s.add_runtime_dependency(%q, ["~> 3.2015"]) s.add_development_dependency(%q, ["~> 5.9"]) s.add_development_dependency(%q, ["~> 1.0"]) s.add_development_dependency(%q, ["~> 2.0"]) s.add_development_dependency(%q, ["~> 1.0"]) s.add_development_dependency(%q, ["~> 1.4"]) s.add_development_dependency(%q, ["~> 5.2"]) s.add_development_dependency(%q, ["~> 10.0"]) s.add_development_dependency(%q, ["~> 4.0"]) s.add_development_dependency(%q, ["~> 0.7"]) else s.add_dependency(%q, ["~> 1.3"]) s.add_dependency(%q, ["~> 3.15"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.1"]) s.add_dependency(%q, ["~> 1.6"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.2"]) s.add_dependency(%q, ["~> 3.2015"]) s.add_dependency(%q, ["~> 5.9"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 2.0"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.4"]) s.add_dependency(%q, ["~> 5.2"]) s.add_dependency(%q, ["~> 10.0"]) s.add_dependency(%q, ["~> 4.0"]) s.add_dependency(%q, ["~> 0.7"]) end else s.add_dependency(%q, ["~> 1.3"]) s.add_dependency(%q, ["~> 3.15"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.1"]) s.add_dependency(%q, ["~> 1.6"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.2"]) s.add_dependency(%q, ["~> 3.2015"]) s.add_dependency(%q, ["~> 5.9"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 2.0"]) s.add_dependency(%q, ["~> 1.0"]) s.add_dependency(%q, ["~> 1.4"]) s.add_dependency(%q, ["~> 5.2"]) s.add_dependency(%q, ["~> 10.0"]) s.add_dependency(%q, ["~> 4.0"]) s.add_dependency(%q, ["~> 0.7"]) end end