fontist 1.7.3 → 1.8.5
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 +4 -4
- data/.github/workflows/release.yml +38 -0
- data/.github/workflows/rspec.yml +58 -0
- data/README.md +48 -4
- data/{bin → exe}/fontist +0 -0
- data/fontist.gemspec +10 -7
- data/lib/fontist.rb +9 -2
- data/lib/fontist/cli.rb +64 -55
- data/lib/fontist/errors.rb +63 -12
- data/lib/fontist/font.rb +33 -64
- data/lib/fontist/font_installer.rb +118 -0
- data/lib/fontist/font_path.rb +29 -0
- data/lib/fontist/fontist_font.rb +3 -49
- data/lib/fontist/formula.rb +101 -35
- data/lib/fontist/formula_paths.rb +43 -0
- data/lib/fontist/helpers.rb +7 -0
- data/lib/fontist/import/create_formula.rb +3 -2
- data/lib/fontist/import/extractors.rb +4 -0
- data/lib/fontist/import/extractors/cpio_extractor.rb +39 -0
- data/lib/fontist/import/extractors/gzip_extractor.rb +27 -0
- data/lib/fontist/import/extractors/rpm_extractor.rb +45 -0
- data/lib/fontist/import/extractors/tar_extractor.rb +47 -0
- data/lib/fontist/import/google/skiplist.yml +3 -0
- data/lib/fontist/import/google_check.rb +1 -1
- data/lib/fontist/import/google_import.rb +3 -4
- data/lib/fontist/import/otfinfo_generate.rb +1 -1
- data/lib/fontist/import/recursive_extraction.rb +26 -8
- data/lib/fontist/import/sil_import.rb +99 -0
- data/lib/fontist/index.rb +11 -0
- data/lib/fontist/indexes/base_index.rb +82 -0
- data/lib/fontist/indexes/filename_index.rb +19 -0
- data/lib/fontist/indexes/font_index.rb +21 -0
- data/lib/fontist/indexes/index_formula.rb +36 -0
- data/lib/fontist/manifest/install.rb +4 -5
- data/lib/fontist/manifest/locations.rb +9 -1
- data/lib/fontist/system_font.rb +32 -62
- data/lib/fontist/system_index.rb +47 -5
- data/lib/fontist/utils.rb +5 -0
- data/lib/fontist/utils/cache.rb +12 -4
- data/lib/fontist/utils/cpio/cpio.rb +199 -0
- data/lib/fontist/utils/cpio_extractor.rb +47 -0
- data/lib/fontist/utils/exe_extractor.rb +1 -1
- data/lib/fontist/utils/gzip_extractor.rb +24 -0
- data/lib/fontist/utils/locking.rb +17 -0
- data/lib/fontist/utils/rpm_extractor.rb +37 -0
- data/lib/fontist/utils/tar_extractor.rb +61 -0
- data/lib/fontist/utils/zip_extractor.rb +1 -1
- data/lib/fontist/version.rb +1 -1
- metadata +74 -26
- data/.github/workflows/macosx.yml +0 -33
- data/.github/workflows/ubuntu.yml +0 -30
- data/.github/workflows/windows.yml +0 -32
- data/bin/check_google +0 -8
- data/bin/console +0 -11
- data/bin/convert_formulas +0 -8
- data/bin/generate_otfinfo +0 -8
- data/bin/import_google +0 -8
- data/bin/rspec +0 -29
- data/bin/setup +0 -7
- data/lib/fontist/font_formula.rb +0 -169
- data/lib/fontist/formula_template.rb +0 -122
- data/lib/fontist/formulas.rb +0 -56
- data/lib/fontist/registry.rb +0 -43
data/lib/fontist/formula.rb
CHANGED
@@ -1,50 +1,43 @@
|
|
1
|
+
require "fontist/index"
|
2
|
+
require "fontist/helpers"
|
3
|
+
require "git"
|
4
|
+
|
1
5
|
module Fontist
|
2
6
|
class Formula
|
3
|
-
def
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
7
|
+
def self.update_formulas_repo
|
8
|
+
if Dir.exist?(Fontist.formulas_repo_path)
|
9
|
+
Git.open(Fontist.formulas_repo_path).pull
|
10
|
+
else
|
11
|
+
Git.clone(Fontist.formulas_repo_url,
|
12
|
+
Fontist.formulas_repo_path,
|
13
|
+
depth: 1)
|
14
|
+
end
|
8
15
|
end
|
9
16
|
|
10
17
|
def self.all
|
11
|
-
|
18
|
+
Dir[Fontist.formulas_path.join("**/*.yml").to_s].map do |path|
|
19
|
+
Formula.new_from_file(path)
|
20
|
+
end
|
12
21
|
end
|
13
22
|
|
14
23
|
def self.find(font_name)
|
15
|
-
|
24
|
+
Indexes::FontIndex.from_yaml.load_formulas(font_name).first
|
16
25
|
end
|
17
26
|
|
18
|
-
def self.find_fonts(
|
19
|
-
|
20
|
-
end
|
21
|
-
|
22
|
-
def self.find_styles(font, style)
|
23
|
-
new(font_name: font, style_name: style).find_styles
|
24
|
-
end
|
27
|
+
def self.find_fonts(font_name)
|
28
|
+
formulas = Indexes::FontIndex.from_yaml.load_formulas(font_name)
|
25
29
|
|
26
|
-
|
27
|
-
@all ||= Fontist::Registry.instance.formulas
|
28
|
-
end
|
29
|
-
|
30
|
-
def find
|
31
|
-
formulas.values.detect do |formula|
|
32
|
-
formula.fonts.any? do |f|
|
33
|
-
f.name.casecmp?(font_name)
|
34
|
-
end
|
35
|
-
end
|
36
|
-
end
|
37
|
-
|
38
|
-
def find_fonts
|
39
|
-
formulas.values.map do |formula|
|
30
|
+
formulas.map do |formula|
|
40
31
|
formula.fonts.select do |f|
|
41
32
|
f.name.casecmp?(font_name)
|
42
33
|
end
|
43
34
|
end.flatten
|
44
35
|
end
|
45
36
|
|
46
|
-
def find_styles
|
47
|
-
formulas.
|
37
|
+
def self.find_styles(font_name, style_name)
|
38
|
+
formulas = Indexes::FontIndex.from_yaml.load_formulas(font_name)
|
39
|
+
|
40
|
+
formulas.map do |formula|
|
48
41
|
formula.fonts.map do |f|
|
49
42
|
f.styles.select do |s|
|
50
43
|
f.name.casecmp?(font_name) && s.type.casecmp?(style_name)
|
@@ -53,16 +46,89 @@ module Fontist
|
|
53
46
|
end.flatten
|
54
47
|
end
|
55
48
|
|
49
|
+
def self.new_from_file(path)
|
50
|
+
data = YAML.load_file(path)
|
51
|
+
new(data, path)
|
52
|
+
end
|
53
|
+
|
54
|
+
def initialize(data, path)
|
55
|
+
@data = data
|
56
|
+
@path = path
|
57
|
+
end
|
58
|
+
|
59
|
+
def to_index_formula
|
60
|
+
Indexes::IndexFormula.new(path)
|
61
|
+
end
|
62
|
+
|
63
|
+
def path
|
64
|
+
@path
|
65
|
+
end
|
66
|
+
|
67
|
+
def key
|
68
|
+
@data["key"] || default_key
|
69
|
+
end
|
70
|
+
|
71
|
+
def description
|
72
|
+
@data["description"]
|
73
|
+
end
|
74
|
+
|
75
|
+
def homepage
|
76
|
+
@data["homepage"]
|
77
|
+
end
|
78
|
+
|
79
|
+
def copyright
|
80
|
+
@data["copyright"]
|
81
|
+
end
|
82
|
+
|
83
|
+
def license_url
|
84
|
+
@data["license_url"]
|
85
|
+
end
|
86
|
+
|
87
|
+
def license
|
88
|
+
@data["open_license"] || @data["requires_license_agreement"]
|
89
|
+
end
|
90
|
+
|
91
|
+
def license_required
|
92
|
+
@data["requires_license_agreement"] ? true : false
|
93
|
+
end
|
94
|
+
|
95
|
+
def extract
|
96
|
+
Helpers.parse_to_object(@data["extract"])
|
97
|
+
end
|
98
|
+
|
99
|
+
def resources
|
100
|
+
Helpers.parse_to_object(@data["resources"].values)
|
101
|
+
end
|
102
|
+
|
103
|
+
def fonts
|
104
|
+
@fonts ||= Helpers.parse_to_object(hash_collection_fonts + hash_fonts)
|
105
|
+
end
|
106
|
+
|
56
107
|
private
|
57
108
|
|
58
|
-
|
109
|
+
def default_key
|
110
|
+
escaped = Regexp.escape(Fontist.formulas_path.to_s + "/")
|
111
|
+
@path.sub(Regexp.new("^" + escaped), "").sub(/\.yml$/, "")
|
112
|
+
end
|
113
|
+
|
114
|
+
def hash_collection_fonts
|
115
|
+
return [] unless @data["font_collections"]
|
116
|
+
|
117
|
+
@data["font_collections"].flat_map do |coll|
|
118
|
+
filenames = { "font" => coll["filename"],
|
119
|
+
"source_font" => coll["source_filename"] }
|
59
120
|
|
60
|
-
|
61
|
-
|
121
|
+
coll["fonts"].map do |font|
|
122
|
+
{ "name" => font["name"],
|
123
|
+
"styles" => font["styles"].map { |s| filenames.merge(s) } }
|
124
|
+
end
|
125
|
+
end
|
62
126
|
end
|
63
127
|
|
64
|
-
def
|
65
|
-
|
128
|
+
def hash_fonts
|
129
|
+
return [] unless @data["fonts"]
|
130
|
+
|
131
|
+
@data["fonts"]
|
66
132
|
end
|
67
133
|
end
|
68
134
|
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
module Fontist
|
2
|
+
class FormulaPaths
|
3
|
+
attr_reader :font_paths
|
4
|
+
|
5
|
+
def initialize(font_paths)
|
6
|
+
@font_paths = font_paths
|
7
|
+
end
|
8
|
+
|
9
|
+
def find(font, style = nil)
|
10
|
+
styles = find_styles_by_formulas(font, style)
|
11
|
+
return if styles.empty?
|
12
|
+
|
13
|
+
fonts = styles.uniq { |s| s["font"] }.flat_map do |s|
|
14
|
+
paths = search_font_paths(s["font"])
|
15
|
+
paths.map do |path|
|
16
|
+
{ full_name: s["full_name"],
|
17
|
+
path: path }
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
fonts.empty? ? nil : fonts
|
22
|
+
end
|
23
|
+
|
24
|
+
private
|
25
|
+
|
26
|
+
def find_styles_by_formulas(font, style)
|
27
|
+
if style
|
28
|
+
Formula.find_styles(font, style)
|
29
|
+
else
|
30
|
+
fonts = Formula.find_fonts(font)
|
31
|
+
return [] unless fonts
|
32
|
+
|
33
|
+
fonts.flat_map(&:styles)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def search_font_paths(filename)
|
38
|
+
font_paths.select do |path|
|
39
|
+
File.basename(path) == filename
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
@@ -50,9 +50,10 @@ module Fontist
|
|
50
50
|
|
51
51
|
def save(hash)
|
52
52
|
filename = Import.name_to_filename(hash[:name])
|
53
|
+
path = @options[:formula_dir] ? File.join(@options[:formula_dir], filename) : filename
|
53
54
|
yaml = YAML.dump(Helpers::HashHelper.stringify_keys(hash))
|
54
|
-
File.write(
|
55
|
-
|
55
|
+
File.write(path, yaml)
|
56
|
+
path
|
56
57
|
end
|
57
58
|
end
|
58
59
|
end
|
@@ -3,3 +3,7 @@ require_relative "extractors/zip_extractor"
|
|
3
3
|
require_relative "extractors/ole_extractor"
|
4
4
|
require_relative "extractors/seven_zip_extractor"
|
5
5
|
require_relative "extractors/cab_extractor"
|
6
|
+
require_relative "extractors/rpm_extractor"
|
7
|
+
require_relative "extractors/gzip_extractor"
|
8
|
+
require_relative "extractors/cpio_extractor"
|
9
|
+
require_relative "extractors/tar_extractor"
|
@@ -0,0 +1,39 @@
|
|
1
|
+
module Fontist
|
2
|
+
module Import
|
3
|
+
module Extractors
|
4
|
+
class CpioExtractor < Extractor
|
5
|
+
def extract
|
6
|
+
dir = Dir.mktmpdir
|
7
|
+
extract_cpio(@archive, dir)
|
8
|
+
dir
|
9
|
+
end
|
10
|
+
|
11
|
+
def format
|
12
|
+
"cpio"
|
13
|
+
end
|
14
|
+
|
15
|
+
private
|
16
|
+
|
17
|
+
def extract_cpio(archive, dir)
|
18
|
+
archive_file = File.open(archive, "rb")
|
19
|
+
|
20
|
+
reader_class.new(archive_file).each do |entry, file|
|
21
|
+
path = File.join(dir, entry.name)
|
22
|
+
if entry.directory?
|
23
|
+
FileUtils.mkdir_p(path)
|
24
|
+
else
|
25
|
+
File.write(path, file.read)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def reader_class
|
31
|
+
@reader_class ||= begin
|
32
|
+
require "fontist/utils/cpio/cpio"
|
33
|
+
CPIO::ASCIIReader
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module Fontist
|
2
|
+
module Import
|
3
|
+
module Extractors
|
4
|
+
class GzipExtractor < Extractor
|
5
|
+
def extract
|
6
|
+
dir = Dir.mktmpdir
|
7
|
+
extract_gzip(@archive, dir)
|
8
|
+
dir
|
9
|
+
end
|
10
|
+
|
11
|
+
def format
|
12
|
+
"gzip"
|
13
|
+
end
|
14
|
+
|
15
|
+
private
|
16
|
+
|
17
|
+
def extract_gzip(archive, dir)
|
18
|
+
Zlib::GzipReader.open(archive) do |gz|
|
19
|
+
basename = File.basename(archive, ".*")
|
20
|
+
path = File.join(dir, basename)
|
21
|
+
File.write(path, gz.read)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,45 @@
|
|
1
|
+
module Fontist
|
2
|
+
module Import
|
3
|
+
module Extractors
|
4
|
+
class RpmExtractor < Extractor
|
5
|
+
def extract
|
6
|
+
dir = Dir.mktmpdir
|
7
|
+
extract_rpm(@archive, dir)
|
8
|
+
dir
|
9
|
+
end
|
10
|
+
|
11
|
+
def format
|
12
|
+
"rpm"
|
13
|
+
end
|
14
|
+
|
15
|
+
private
|
16
|
+
|
17
|
+
def extract_rpm(archive, dir)
|
18
|
+
file = File.open(archive, "rb")
|
19
|
+
rpm = rpm_class.new(file)
|
20
|
+
content = rpm.payload.read
|
21
|
+
path = target_path(archive, rpm.tags, dir)
|
22
|
+
|
23
|
+
File.write(path, content)
|
24
|
+
ensure
|
25
|
+
file.close
|
26
|
+
end
|
27
|
+
|
28
|
+
def rpm_class
|
29
|
+
@rpm_class ||= begin
|
30
|
+
require "arr-pm"
|
31
|
+
RPM::File
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
def target_path(archive, tags, dir)
|
36
|
+
archive_format = tags[:payloadformat]
|
37
|
+
compression_format = tags[:payloadcompressor] == "gzip" ? "gz" : tags[:payloadcompressor]
|
38
|
+
basename = File.basename(archive, ".*")
|
39
|
+
filename = basename + "." + archive_format + "." + compression_format
|
40
|
+
File.join(dir, filename)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
module Fontist
|
2
|
+
module Import
|
3
|
+
module Extractors
|
4
|
+
class TarExtractor < Extractor
|
5
|
+
def extract
|
6
|
+
dir = Dir.mktmpdir
|
7
|
+
extract_tar(@archive, dir)
|
8
|
+
dir
|
9
|
+
end
|
10
|
+
|
11
|
+
def format
|
12
|
+
"tar"
|
13
|
+
end
|
14
|
+
|
15
|
+
private
|
16
|
+
|
17
|
+
def extract_tar(archive, dir)
|
18
|
+
archive_file = File.open(archive, "rb")
|
19
|
+
reader_class.new(archive_file) do |tar|
|
20
|
+
tar.each do |tarfile|
|
21
|
+
save_tar_file(tarfile, dir)
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def reader_class
|
27
|
+
@reader_class ||= begin
|
28
|
+
require "rubygems/package"
|
29
|
+
Gem::Package::TarReader
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def save_tar_file(file, dir)
|
34
|
+
path = File.join(dir, file.full_name)
|
35
|
+
|
36
|
+
if file.directory?
|
37
|
+
FileUtils.mkdir_p(path)
|
38
|
+
else
|
39
|
+
File.open(path, "wb") do |f|
|
40
|
+
f.print(file.read)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -156,10 +156,9 @@ module Fontist
|
|
156
156
|
h.merge!(family_name: style.family_name,
|
157
157
|
type: style.style,
|
158
158
|
full_name: style.full_name)
|
159
|
-
h.merge!(style.to_h.
|
160
|
-
|
161
|
-
|
162
|
-
:copyright).compact)
|
159
|
+
h.merge!(style.to_h.select do |k, _|
|
160
|
+
%i(post_script_name version description copyright).include?(k)
|
161
|
+
end.compact)
|
163
162
|
h.merge!(font: fix_variable_filename(style.filename))
|
164
163
|
end
|
165
164
|
end
|
@@ -25,7 +25,7 @@ module Fontist
|
|
25
25
|
def font_paths(font)
|
26
26
|
formula = Fontist::Formula.find(font)
|
27
27
|
font_formula = Object.const_get(formula.installer)
|
28
|
-
font_formula.
|
28
|
+
font_formula.install(confirmation: "yes")
|
29
29
|
end
|
30
30
|
|
31
31
|
def generate_styles(paths)
|