best_type 0.0.10 → 1.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 29fe983eac1114ba38d161af60db4bc5baaed14ffc7f9fa226ec0ce9f6b9658b
4
- data.tar.gz: 2d8c71566c13afaf5f48253ad659a4aad8c4f345403e0067ad6bc08b793f6451
3
+ metadata.gz: b59a909ec727b9062dbdcf5b47b63f714eaf43367dfeef9fa70cb282e4fe6e2d
4
+ data.tar.gz: fe0c23aeff8d9b2473d41182119740ca8e9ff94e84abf903720454a9e58a5290
5
5
  SHA512:
6
- metadata.gz: 905b6b2f3bf244668bc1962eea0561cd267e7aaee333c2c4817f56ca917b7181c0d55cddfbaa952032ed839aa75422d1c3a75ee0b5b17fecf7ea826a8a4f8c28
7
- data.tar.gz: a96af2728b2d1c5c15fdbb4a3a065be91d11352f81c8ab1a6ee38a517e737bc6c97625538a17a985015b58ee21332c13fded4160964f42c0189ea44bf155d7cf
6
+ metadata.gz: 13d9eb9c134947762ab702394539f713d4ea20ec304111170804fa9c5d2b01c56b0cb6854f8cde0af84d461e796f064dbce0ab57d63f7c6583647e410d255b30
7
+ data.tar.gz: 9f495fb0ff1a4f357f8922ed8dbaafcdf436a89c4669d751ccc7d5193c4eef1577771917adc9ee64a06d03ca6149fef441e97cf3e06ebcdd8eaedec724873c9b
data/README.md CHANGED
@@ -50,9 +50,10 @@ BestType.configure({
50
50
  BestType.mime_type.for_file_name('myfile.custom') # 'custom/type'
51
51
  BestType.dc_type.for_file_name('myfile.custom') # 'CustomDC'
52
52
  BestType.pcdm_type.for_mime_type('custom/type') # 'CustomPCDM'
53
-
54
53
  ```
55
54
 
55
+ **Note: Case-insensitive string comparisons are used when checking against file extensions and mime types.**
56
+
56
57
  ### Recommended Setup For Rails
57
58
 
58
59
  Add best_type to your Gemfile:
@@ -93,7 +94,7 @@ development:
93
94
  'good/type': 'Good'
94
95
  mime_type_to_pcdm_type_overrides:
95
96
  'good/type': 'Goodly'
96
-
97
+
97
98
  test:
98
99
  extension_to_mime_type_overrides:
99
100
  'better': 'better/type'
@@ -1,12 +1,17 @@
1
1
  extension_to_mime_type_overrides:
2
+ # NOTE: Always use lower case keys
2
3
  'test': 'test/type'
3
4
  'mp4': 'video/mp4'
4
5
  'vtt': 'text/vtt'
5
6
  'm4v': 'video/x-m4v'
7
+ 'mts': 'video/MP2T'
8
+ 'ac3': 'audio/ac3'
6
9
  mime_type_to_dc_type_overrides:
10
+ # NOTE: Always use lower case keys
7
11
  'test/type': 'Test'
8
12
  'application/mxf': 'MovingImage'
9
13
  'application/vnd.openxmlformats-officedocument.wordprocessingml.document': 'Text'
10
14
  'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet': 'Dataset'
11
15
  mime_type_to_pcdm_type_overrides:
16
+ # NOTE: Always use lower case keys
12
17
  'test/type': 'Test'
@@ -1,6 +1,10 @@
1
+ # frozen_string_literal: true
2
+
3
+ # rubocop:disable Metrics/AbcSize
4
+ # rubocop:disable Metrics/MethodLength
5
+
1
6
  module BestType
2
7
  class Config
3
-
4
8
  attr_reader :extension_to_mime_type_overrides, :mime_type_to_dc_type_overrides, :mime_type_to_pcdm_type_overrides
5
9
 
6
10
  def initialize(user_config_options = {})
@@ -14,23 +18,34 @@ module BestType
14
18
  @mime_type_to_pcdm_type_overrides = internal_config_options['mime_type_to_pcdm_type_overrides'] || {}
15
19
 
16
20
  stringify_user_config_options_keys!(user_config_options)
17
- add_extension_to_mime_type_overrides(user_config_options['extension_to_mime_type_overrides']) if user_config_options.key?('extension_to_mime_type_overrides')
18
- add_mime_type_to_dc_type_overrides(user_config_options['mime_type_to_dc_type_overrides']) if user_config_options.key?('mime_type_to_dc_type_overrides')
19
- add_mime_type_to_pcdm_type_overrides(user_config_options['mime_type_to_pcdm_type_overrides']) if user_config_options.key?('mime_type_to_pcdm_type_overrides')
21
+ if user_config_options.key?('extension_to_mime_type_overrides')
22
+ add_extension_to_mime_type_overrides(user_config_options['extension_to_mime_type_overrides'])
23
+ end
24
+ if user_config_options.key?('mime_type_to_dc_type_overrides')
25
+ add_mime_type_to_dc_type_overrides(user_config_options['mime_type_to_dc_type_overrides'])
26
+ end
27
+ return unless user_config_options.key?('mime_type_to_pcdm_type_overrides')
28
+
29
+ add_mime_type_to_pcdm_type_overrides(user_config_options['mime_type_to_pcdm_type_overrides'])
20
30
  end
21
31
 
22
32
  private
23
33
 
34
+ # Returns a new Hash with downcased keys
35
+ def downcase_hash_keys(hsh)
36
+ hsh.transform_keys(&:downcase)
37
+ end
38
+
24
39
  def add_extension_to_mime_type_overrides(overrides)
25
- @extension_to_mime_type_overrides.merge!(overrides)
40
+ @extension_to_mime_type_overrides.merge!(downcase_hash_keys(overrides))
26
41
  end
27
42
 
28
43
  def add_mime_type_to_dc_type_overrides(overrides)
29
- @mime_type_to_dc_type_overrides.merge!(overrides)
44
+ @mime_type_to_dc_type_overrides.merge!(downcase_hash_keys(overrides))
30
45
  end
31
46
 
32
47
  def add_mime_type_to_pcdm_type_overrides(overrides)
33
- @mime_type_to_pcdm_type_overrides.merge!(overrides)
48
+ @mime_type_to_pcdm_type_overrides.merge!(downcase_hash_keys(overrides))
34
49
  end
35
50
 
36
51
  def stringify_user_config_options_keys!(user_config_options)
@@ -43,6 +58,5 @@ module BestType
43
58
  end
44
59
  user_config_options_keys
45
60
  end
46
-
47
61
  end
48
62
  end
@@ -1,19 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ # rubocop:disable Metrics/MethodLength
4
+
1
5
  module BestType
2
6
  class DcTypeLookup
3
-
4
7
  attr_reader :config
5
8
 
6
- COLLECTION = 'Collection'.freeze
7
- DATASET = 'Dataset'.freeze
8
- EVENT = 'Event'.freeze
9
- INTERACTIVE_RESOURCE = 'InteractiveResource'.freeze
10
- MOVING_IMAGE = 'MovingImage'.freeze
11
- PHYSICAL_OBJECT = 'PhysicalObject'.freeze
12
- SERVICE = 'Service'.freeze
13
- SOFTWARE = 'Software'.freeze
14
- SOUND = 'Sound'.freeze
15
- STILL_IMAGE = 'StillImage'.freeze
16
- TEXT = 'Text'.freeze
9
+ COLLECTION = 'Collection'
10
+ DATASET = 'Dataset'
11
+ EVENT = 'Event'
12
+ INTERACTIVE_RESOURCE = 'InteractiveResource'
13
+ MOVING_IMAGE = 'MovingImage'
14
+ PHYSICAL_OBJECT = 'PhysicalObject'
15
+ SERVICE = 'Service'
16
+ SOFTWARE = 'Software'
17
+ SOUND = 'Sound'
18
+ STILL_IMAGE = 'StillImage'
19
+ TEXT = 'Text'
17
20
 
18
21
  # these include values that will not be derived from MIME/content types
19
22
  VALID_TYPES = [
@@ -37,10 +40,16 @@ module BestType
37
40
  end
38
41
 
39
42
  def for_file_name(file_name_or_path)
43
+ # Normalize format of file_name_or_path
44
+ file_name_or_path = file_name_or_path.downcase
45
+
40
46
  for_mime_type(@mime_type_lookup.for_file_name(file_name_or_path))
41
47
  end
42
48
 
43
49
  def for_mime_type(mime_type)
50
+ # Normalize format of mime_type
51
+ mime_type = mime_type.downcase
52
+
44
53
  # Check config overrides first
45
54
  dc_type = @config.mime_type_to_dc_type_overrides.fetch(mime_type, nil)
46
55
  return dc_type unless dc_type.nil?
@@ -50,14 +59,13 @@ module BestType
50
59
  /^video/ => MOVING_IMAGE,
51
60
  /^audio/ => SOUND,
52
61
  /^text/ => TEXT,
53
- /^application\/(pdf|msword)/ => TEXT,
54
- /excel|spreadsheet|xls|application\/sql/ => DATASET,
62
+ %r{^application/(pdf|msword)} => TEXT,
63
+ %r{excel|spreadsheet|xls|application/sql} => DATASET,
55
64
  /^application/ => SOFTWARE
56
65
  }
57
66
 
58
67
  dc_type = mimes_to_dc.find { |pattern, _type_val| mime_type =~ pattern }
59
68
  dc_type.nil? ? FALLBACK_DC_TYPE : dc_type.last
60
69
  end
61
-
62
70
  end
63
71
  end
@@ -1,19 +1,23 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'mime-types'
2
4
 
3
5
  module BestType
4
6
  class MimeTypeLookup
5
-
6
7
  attr_reader :config
7
8
 
8
- FALLBACK_MIME_TYPE_VALUE = 'application/octet-stream'.freeze
9
+ FALLBACK_MIME_TYPE_VALUE = 'application/octet-stream'
9
10
 
10
11
  def initialize(config)
11
12
  @config = config
12
13
  end
13
14
 
14
15
  def for_file_name(file_name_or_path)
16
+ # Normalize format of file_name_or_path
17
+ file_name_or_path = file_name_or_path.downcase
18
+
15
19
  extension = File.extname(file_name_or_path)
16
- extension = extension[1..-1] unless extension.empty?
20
+ extension = extension[1..] unless extension.empty?
17
21
 
18
22
  # Check config overrides first
19
23
  unless extension.empty?
@@ -25,6 +29,5 @@ module BestType
25
29
  detected_mime_types = MIME::Types.of(file_name_or_path)
26
30
  detected_mime_types.empty? ? FALLBACK_MIME_TYPE_VALUE : detected_mime_types.first.content_type
27
31
  end
28
-
29
32
  end
30
33
  end
@@ -1,28 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ # rubocop:disable Metrics/AbcSize
4
+ # rubocop:disable Metrics/CyclomaticComplexity
5
+ # rubocop:disable Metrics/MethodLength
6
+
1
7
  module BestType
2
8
  class PcdmTypeLookup
3
-
4
9
  attr_reader :config
5
10
 
6
11
  # https://github.com/duraspace/pcdm/blob/master/pcdm-ext/file-format-types.rdf
7
- ARCHIVE = "Archive".freeze
8
- AUDIO = "Audio".freeze
9
- DATABASE = "Database".freeze
10
- DATASET = "Dataset".freeze
11
- EMAIL = "Email".freeze
12
- FONT = "Font".freeze
13
- HTML = "HTML".freeze
14
- IMAGE = "Image".freeze
15
- PAGE_DESCRIPTION = "PageDescription".freeze
16
- PRESENTATION = "Presentation".freeze
17
- SOFTWARE = "Software".freeze
18
- SOURCE_CODE = "SourceCode".freeze
19
- SPREADSHEET = "Spreadsheet".freeze
20
- STRUCTURED_TEXT = "StructuredText".freeze
21
- TEXT = "Text".freeze
22
- UNKNOWN = "Unknown".freeze
23
- UNSTRUCTURED_TEXT = "UnstructuredText".freeze
24
- VIDEO = "Video".freeze
25
- WEBSITE = "Website".freeze
12
+ ARCHIVE = 'Archive'
13
+ AUDIO = 'Audio'
14
+ DATABASE = 'Database'
15
+ DATASET = 'Dataset'
16
+ EMAIL = 'Email'
17
+ FONT = 'Font'
18
+ HTML = 'HTML'
19
+ IMAGE = 'Image'
20
+ PAGE_DESCRIPTION = 'PageDescription'
21
+ PRESENTATION = 'Presentation'
22
+ SOFTWARE = 'Software'
23
+ SOURCE_CODE = 'SourceCode'
24
+ SPREADSHEET = 'Spreadsheet'
25
+ STRUCTURED_TEXT = 'StructuredText'
26
+ TEXT = 'Text'
27
+ UNKNOWN = 'Unknown'
28
+ UNSTRUCTURED_TEXT = 'UnstructuredText'
29
+ VIDEO = 'Video'
30
+ WEBSITE = 'Website'
26
31
 
27
32
  # these include values that will not be derived from MIME/content types
28
33
  VALID_TYPES = [
@@ -46,10 +51,16 @@ module BestType
46
51
  end
47
52
 
48
53
  def for_file_name(file_name_or_path)
54
+ # Normalize format of file_name_or_path
55
+ file_name_or_path = file_name_or_path.downcase
56
+
49
57
  for_mime_type(@mime_type_lookup.for_file_name(file_name_or_path))
50
58
  end
51
59
 
52
60
  def for_mime_type(mime_type)
61
+ # Normalize format of mime_type
62
+ mime_type = mime_type.downcase
63
+
53
64
  # Check config overrides first
54
65
  file_type = @config.mime_type_to_pcdm_type_overrides.fetch(mime_type, nil)
55
66
  return file_type unless file_type.nil?
@@ -59,58 +70,56 @@ module BestType
59
70
  /^video/i => VIDEO,
60
71
  /^audio/i => AUDIO,
61
72
  /^text/i => {
62
- /\/css/i => SOURCE_CODE,
63
- /\/html/i => HTML,
73
+ %r{/css}i => SOURCE_CODE,
74
+ %r{/html}i => HTML,
64
75
  /.+/ => TEXT
65
76
  },
66
77
  /excel|spreadsheet|xls/i => SPREADSHEET,
67
- /application\/sql/i => DATABASE,
78
+ %r{application/sql}i => DATABASE,
68
79
  /csv/i => DATASET,
69
80
  /octet.stream/i => UNKNOWN,
70
81
  /^application/i => {
71
- /\/access/i => DATABASE,
72
- /\/css/i => SOURCE_CODE,
73
- /\/html/i => HTML,
74
- /\/x-iwork-keynote/i => PRESENTATION,
75
- /\/x-iwork-numbers/i => SPREADSHEET,
76
- /\/x-iwork-pages/i => PAGE_DESCRIPTION,
77
- /\/mbox/i => EMAIL,
78
- /\/mp4/i => VIDEO,
79
- /\/mp4a/i => AUDIO,
80
- /\/msaccess/i => DATABASE,
81
- /\/mxf/i => VIDEO,
82
- /\/(pdf|msword)/i => PAGE_DESCRIPTION,
83
- /\/postscript/i => PAGE_DESCRIPTION,
84
- /\/powerpoint/i => PRESENTATION,
85
- /\/rtf/i => PAGE_DESCRIPTION,
86
- /\/sql/i => DATABASE,
87
- /\/swf/ => VIDEO,
88
- /\/vnd.ms-asf/i => VIDEO,
89
- /\/vnd.ms-word/i => PAGE_DESCRIPTION,
90
- /\/vnd.ms-wpl/i => PAGE_DESCRIPTION,
91
- /\/vnd.oasis.opendocument.text/i => PAGE_DESCRIPTION,
92
- /\/vnd.openxmlformats-officedocument.presentation/i => PRESENTATION,
93
- /\/vnd.openxmlformats-officedocument.wordprocessingml/i => PAGE_DESCRIPTION,
94
- /\/vnd.ms-powerpoint/i => PRESENTATION,
95
- /\/vnd.sun.xml.calc/i => SPREADSHEET,
96
- /\/vnd.sun.xml.impress/i => PRESENTATION,
97
- /\/vnd.sun.xml.writer/i => PAGE_DESCRIPTION,
98
- /\/xml/i => STRUCTURED_TEXT,
99
- /\/x.mspublisher/i => PAGE_DESCRIPTION,
100
- /\/x.shockwave-flash/ => VIDEO,
101
- /\/x.spss/i => DATASET,
102
- /\/zip/i => ARCHIVE,
82
+ %r{/access}i => DATABASE,
83
+ %r{/css}i => SOURCE_CODE,
84
+ %r{/html}i => HTML,
85
+ %r{/x-iwork-keynote}i => PRESENTATION,
86
+ %r{/x-iwork-numbers}i => SPREADSHEET,
87
+ %r{/x-iwork-pages}i => PAGE_DESCRIPTION,
88
+ %r{/mbox}i => EMAIL,
89
+ %r{/mp4}i => VIDEO,
90
+ %r{/mp4a}i => AUDIO,
91
+ %r{/msaccess}i => DATABASE,
92
+ %r{/mxf}i => VIDEO,
93
+ %r{/(pdf|msword)}i => PAGE_DESCRIPTION,
94
+ %r{/postscript}i => PAGE_DESCRIPTION,
95
+ %r{/powerpoint}i => PRESENTATION,
96
+ %r{/rtf}i => PAGE_DESCRIPTION,
97
+ %r{/sql}i => DATABASE,
98
+ %r{/swf} => VIDEO,
99
+ %r{/vnd.ms-asf}i => VIDEO,
100
+ %r{/vnd.ms-word}i => PAGE_DESCRIPTION,
101
+ %r{/vnd.ms-wpl}i => PAGE_DESCRIPTION,
102
+ %r{/vnd.oasis.opendocument.text}i => PAGE_DESCRIPTION,
103
+ %r{/vnd.openxmlformats-officedocument.presentation}i => PRESENTATION,
104
+ %r{/vnd.openxmlformats-officedocument.wordprocessingml}i => PAGE_DESCRIPTION,
105
+ %r{/vnd.ms-powerpoint}i => PRESENTATION,
106
+ %r{/vnd.sun.xml.calc}i => SPREADSHEET,
107
+ %r{/vnd.sun.xml.impress}i => PRESENTATION,
108
+ %r{/vnd.sun.xml.writer}i => PAGE_DESCRIPTION,
109
+ %r{/xml}i => STRUCTURED_TEXT,
110
+ %r{/x.mspublisher}i => PAGE_DESCRIPTION,
111
+ %r{/x.shockwave-flash} => VIDEO,
112
+ %r{/x.spss}i => DATASET,
113
+ %r{/zip}i => ARCHIVE,
103
114
  /.+/ => UNKNOWN
104
115
  }
105
116
  }
106
117
 
107
118
  file_type = mimes_to_type.detect { |pattern, _type_val| mime_type =~ pattern }
108
119
  return fallback_type unless file_type
109
- if file_type&.last.is_a? Hash
110
- file_type = file_type.last.detect { |pattern, _type_val| mime_type =~ pattern }
111
- end
120
+
121
+ file_type = file_type.last.detect { |pattern, _type_val| mime_type =~ pattern } if file_type&.last.is_a? Hash
112
122
  file_type.nil? ? fallback_type : file_type.last
113
123
  end
114
-
115
124
  end
116
125
  end
@@ -1,9 +1,9 @@
1
- module BestType
1
+ # frozen_string_literal: true
2
2
 
3
- VERSION = '0.0.10'.freeze
3
+ module BestType
4
+ VERSION = '1.0.1'
4
5
 
5
6
  def self.version
6
7
  VERSION
7
8
  end
8
-
9
9
  end
data/lib/best_type.rb CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'best_type/version'
2
4
  require 'best_type/config'
3
5
  require 'best_type/mime_type_lookup'
@@ -20,7 +22,7 @@ module BestType
20
22
  @pcdm_type ||= BestType::PcdmTypeLookup.new(mime_type)
21
23
  end
22
24
 
23
- def self.config(reload = false, user_config_options = {})
25
+ def self.config(reload: false, user_config_options: {})
24
26
  if @config.nil? || reload
25
27
  @semaphore.synchronize do
26
28
  @config = BestType::Config.new(user_config_options)
@@ -32,7 +34,6 @@ module BestType
32
34
  end
33
35
 
34
36
  def self.configure(opts = {})
35
- config(true, opts)
37
+ config(reload: true, user_config_options: opts)
36
38
  end
37
-
38
39
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: best_type
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.10
4
+ version: 1.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eric O'Hanlon
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: '3.0'
19
+ version: '3.4'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: '3.0'
26
+ version: '3.4'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: rake
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -53,33 +53,19 @@ dependencies:
53
53
  - !ruby/object:Gem::Version
54
54
  version: '3.7'
55
55
  - !ruby/object:Gem::Dependency
56
- name: rubocop
56
+ name: rubocul
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
59
  - - "~>"
60
60
  - !ruby/object:Gem::Version
61
- version: 0.51.0
61
+ version: 4.0.11
62
62
  type: :development
63
63
  prerelease: false
64
64
  version_requirements: !ruby/object:Gem::Requirement
65
65
  requirements:
66
66
  - - "~>"
67
67
  - !ruby/object:Gem::Version
68
- version: 0.51.0
69
- - !ruby/object:Gem::Dependency
70
- name: rubocop-rspec
71
- requirement: !ruby/object:Gem::Requirement
72
- requirements:
73
- - - "~>"
74
- - !ruby/object:Gem::Version
75
- version: 1.20.1
76
- type: :development
77
- prerelease: false
78
- version_requirements: !ruby/object:Gem::Requirement
79
- requirements:
80
- - - "~>"
81
- - !ruby/object:Gem::Version
82
- version: 1.20.1
68
+ version: 4.0.11
83
69
  - !ruby/object:Gem::Dependency
84
70
  name: simplecov
85
71
  requirement: !ruby/object:Gem::Requirement
@@ -129,7 +115,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
129
115
  - !ruby/object:Gem::Version
130
116
  version: '0'
131
117
  requirements: []
132
- rubygems_version: 3.0.8
118
+ rubygems_version: 3.3.26
133
119
  signing_key:
134
120
  specification_version: 4
135
121
  summary: A library for selecting the best mime type or dc type for a file.