jtag 0.1.22 → 0.2.0
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/bin/jtag +271 -377
- data/lib/jtag/config_files/config.yml +2 -3
- data/lib/jtag/jekylltag.rb +225 -272
- data/lib/jtag/string.rb +42 -238
- data/lib/jtag/version.rb +1 -1
- data/lib/jtag.rb +13 -19
- metadata +19 -20
- data/.irbrc +0 -6
- data/CHANGELOG.md +0 -15
- data/Gemfile +0 -3
- data/Jekyll/plugins/autotag_gen.rb +0 -58
- data/Jekyll/source/_layouts/tags_json.html +0 -11
- data/README.md +0 -159
- data/Rakefile +0 -113
- data/jtag.completion.bash +0 -9
- data/jtag.gemspec +0 -25
- data/lib/jtag/array.rb +0 -48
- data/lib/jtag/errors.rb +0 -31
- data/lib/jtag/hash.rb +0 -103
- data/lib/jtag/stupid_json.rb +0 -319
- data/lib/jtag/util.rb +0 -237
- data/mise.toml +0 -2
data/lib/jtag/string.rb
CHANGED
|
@@ -1,244 +1,48 @@
|
|
|
1
|
-
#
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
##
|
|
11
|
-
def to_bool
|
|
12
|
-
case self.downcase
|
|
13
|
-
when /^a/i
|
|
14
|
-
:and
|
|
15
|
-
when /^o/i
|
|
16
|
-
:or
|
|
17
|
-
when /^n/i
|
|
18
|
-
:not
|
|
19
|
-
else
|
|
20
|
-
raise ArgumentError, "Invalid boolean string: #{self}"
|
|
21
|
-
end
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
##
|
|
25
|
-
## Convert a string to a format symbol (:csv, :complete, :json, :plist, :yaml)
|
|
26
|
-
##
|
|
27
|
-
## @return [Symbol] format symbol
|
|
28
|
-
##
|
|
29
|
-
def to_format
|
|
30
|
-
case self.downcase
|
|
31
|
-
when /^j/i
|
|
32
|
-
:json
|
|
33
|
-
when /^p/i
|
|
34
|
-
:plist
|
|
35
|
-
when /^y/i
|
|
36
|
-
:yaml
|
|
37
|
-
when /^cs/i
|
|
38
|
-
:csv
|
|
39
|
-
when /^c/i
|
|
40
|
-
:complete
|
|
41
|
-
else
|
|
42
|
-
raise ArgumentError, "Invalid format string: #{self}"
|
|
43
|
-
end
|
|
44
|
-
end
|
|
45
|
-
|
|
46
|
-
## Check if a string is a list of files
|
|
47
|
-
##
|
|
48
|
-
## @param null [Boolean] check for null-delimited list
|
|
49
|
-
##
|
|
50
|
-
## @example Check if a string is a list of files
|
|
51
|
-
## "file1\nfile2\nfile3".file_list?
|
|
52
|
-
## # => true
|
|
53
|
-
##
|
|
54
|
-
## @return [Boolean]
|
|
55
|
-
def file_list?(null = false)
|
|
56
|
-
self.strip.split(null ? "\x00" : "\n").each do |line|
|
|
57
|
-
return false unless File.exist?(line)
|
|
58
|
-
end
|
|
59
|
-
true
|
|
60
|
-
end
|
|
61
|
-
|
|
62
|
-
##
|
|
63
|
-
## Check if string is YAML
|
|
64
|
-
##
|
|
65
|
-
## @example Check if a string is YAML
|
|
66
|
-
## "tags:\n - tag1\n - tag2".yaml?
|
|
67
|
-
## # => true
|
|
68
|
-
##
|
|
69
|
-
## @example Check if a string is not YAML
|
|
70
|
-
## "test string".yaml?
|
|
71
|
-
## # => false
|
|
72
|
-
##
|
|
73
|
-
## @return [Boolean]
|
|
74
|
-
##
|
|
75
|
-
def yaml?
|
|
76
|
-
begin
|
|
77
|
-
YAML.load(self)
|
|
78
|
-
rescue
|
|
79
|
-
return false
|
|
80
|
-
end
|
|
81
|
-
true
|
|
82
|
-
end
|
|
83
|
-
|
|
84
|
-
##
|
|
85
|
-
## Matches the string against a given keyword based on various options.
|
|
86
|
-
##
|
|
87
|
-
## @param keyword [String] the keyword to match against the string.
|
|
88
|
-
## @param options [Hash] a hash of options to customize the matching behavior.
|
|
89
|
-
## @option options [Boolean] :case_sensitive (false) whether the match should be case-sensitive.
|
|
90
|
-
## @option options [Boolean] :starts_with (false) whether the match should check if the string starts with the keyword.
|
|
91
|
-
## @option options [Boolean] :exact (false) whether the match should be exact.
|
|
92
|
-
## @option options [Boolean] :fuzzy (true) whether the match should be fuzzy.
|
|
93
|
-
## @option options [Integer] :distance (2) the maximum distance between characters for a fuzzy match.
|
|
94
|
-
##
|
|
95
|
-
## @return [Boolean] true if the string matches the keyword based on the given options, false otherwise.
|
|
96
|
-
##
|
|
97
|
-
def match_keyword(keyword, options = {})
|
|
98
|
-
options = {
|
|
99
|
-
case_sensitive: false,
|
|
100
|
-
starts_with: false,
|
|
101
|
-
exact: false,
|
|
102
|
-
fuzzy: false,
|
|
103
|
-
contains: false,
|
|
104
|
-
distance: 2,
|
|
105
|
-
}.merge(options)
|
|
106
|
-
|
|
107
|
-
keyword = Regexp.escape(keyword)
|
|
108
|
-
|
|
109
|
-
if options[:exact]
|
|
110
|
-
re = "^#{keyword}$"
|
|
111
|
-
elsif options[:starts_with]
|
|
112
|
-
re = "^#{keyword}"
|
|
113
|
-
elsif options[:fuzzy]
|
|
114
|
-
re = ".*#{keyword.split(//).join(".{,#{options[:distance] - 1}}")}.*"
|
|
115
|
-
else
|
|
116
|
-
re = ".*#{keyword}.*"
|
|
117
|
-
end
|
|
118
|
-
|
|
119
|
-
if options[:case_sensitive]
|
|
120
|
-
self.match?(/#{re}/)
|
|
121
|
-
else
|
|
122
|
-
self.match?(/#{re}/i)
|
|
123
|
-
end
|
|
124
|
-
end
|
|
125
|
-
|
|
126
|
-
##
|
|
127
|
-
## Check if a string is JSON
|
|
128
|
-
##
|
|
129
|
-
## @example Check if a string is JSON
|
|
130
|
-
## '{"tags": ["tag1", "tag2"]}'.json?
|
|
131
|
-
## # => true
|
|
132
|
-
##
|
|
133
|
-
## @example Check if a string is not JSON
|
|
134
|
-
## "test string".json?
|
|
135
|
-
## # => false
|
|
136
|
-
##
|
|
137
|
-
## @return [Boolean]
|
|
138
|
-
##
|
|
139
|
-
## @note JSON must be a hash or array
|
|
140
|
-
##
|
|
141
|
-
def json?
|
|
142
|
-
begin
|
|
143
|
-
JSON.parse(self).is_a?(Hash) || JSON.parse(self).is_a?(Array)
|
|
144
|
-
rescue
|
|
145
|
-
return false
|
|
146
|
-
end
|
|
147
|
-
true
|
|
148
|
-
end
|
|
149
|
-
|
|
150
|
-
##
|
|
151
|
-
## Convert parenthetical count to hash
|
|
152
|
-
##
|
|
153
|
-
## @example Convert a string to a hash
|
|
154
|
-
## "tag (5)".to_count
|
|
155
|
-
## # => { "name" => "tag", "count" => 5 }
|
|
156
|
-
##
|
|
157
|
-
## @example Convert a string to a hash with no count
|
|
158
|
-
## "tag".to_count
|
|
159
|
-
## # => { "name" => "tag", "count" => 0 }
|
|
160
|
-
##
|
|
161
|
-
## @return [Hash] hash with name and count
|
|
162
|
-
##
|
|
163
|
-
def to_count
|
|
164
|
-
tag = dup.strip.sub(/^[[:punct:]] /, "")
|
|
165
|
-
if tag =~ /(.*) \((\d+)\)/
|
|
166
|
-
{ "name" => $1, "count" => $2.to_i }
|
|
167
|
-
else
|
|
168
|
-
{ "name" => tag, "count" => 0 }
|
|
169
|
-
end
|
|
170
|
-
end
|
|
171
|
-
|
|
172
|
-
##
|
|
173
|
-
## Check if a string is a list of tags
|
|
174
|
-
##
|
|
175
|
-
## @example Check if a string is a list of tags
|
|
176
|
-
## "tag1\ntag2".tag_list?
|
|
177
|
-
## # => true
|
|
178
|
-
##
|
|
179
|
-
## @return [Boolean]
|
|
180
|
-
##
|
|
181
|
-
## @note One tag per line
|
|
182
|
-
## Tags are assumed to be alphanumeric and lowercase
|
|
183
|
-
## (spaces, underscores, and dashes allowed) with no
|
|
184
|
-
## leading or preceding or trailing punctuation
|
|
185
|
-
##
|
|
186
|
-
def tag_list?
|
|
187
|
-
self.strip.split("\n").each do |tag|
|
|
188
|
-
return false unless tag.match?(/^(?![[:punct:]] )[a-z0-9 -_]+(?<![[:punct:]]) *$/)
|
|
189
|
-
end
|
|
190
|
-
true
|
|
191
|
-
end
|
|
192
|
-
|
|
193
|
-
def root_words
|
|
194
|
-
words = break_camel.split("[\s-]")
|
|
195
|
-
words.delete_if { |word| word =~ /^[^a-z]+$/i || word.length < 4 }
|
|
196
|
-
words.map { |word| word = Text::PorterStemming.stem(word).downcase }.join(" ")
|
|
197
|
-
end
|
|
198
|
-
|
|
199
|
-
# convert "WikiLink" to "Wiki link"
|
|
200
|
-
def break_camel
|
|
201
|
-
return downcase if match(/\A[A-Z]+\z/)
|
|
202
|
-
gsub(/([A-Z]+)([A-Z][a-z])/, '\1 \2').
|
|
203
|
-
gsub(/([a-z])([A-Z])/, '\1 \2').
|
|
204
|
-
downcase
|
|
205
|
-
end
|
|
1
|
+
# encoding: utf-8
|
|
2
|
+
class String
|
|
3
|
+
# convert "WikiLink" to "Wiki link"
|
|
4
|
+
def break_camel
|
|
5
|
+
return downcase if match(/\A[A-Z]+\z/)
|
|
6
|
+
gsub(/([A-Z]+)([A-Z][a-z])/, '\1 \2').
|
|
7
|
+
gsub(/([a-z])([A-Z])/, '\1 \2').
|
|
8
|
+
downcase
|
|
9
|
+
end
|
|
206
10
|
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
11
|
+
def strip_markdown
|
|
12
|
+
# strip all Markdown and Liquid tags
|
|
13
|
+
gsub(/\{%.*?%\}/,'').
|
|
14
|
+
gsub(/\[\^.+?\](\: .*?$)?/,'').
|
|
15
|
+
gsub(/\s{0,2}\[.*?\]: .*?$/,'').
|
|
16
|
+
gsub(/\!\[.*?\][\[\(].*?[\]\)]/,"").
|
|
17
|
+
gsub(/\[(.*?)\][\[\(].*?[\]\)]/,"\\1").
|
|
18
|
+
gsub(/^\s{1,2}\[(.*?)\]: (\S+)( ".*?")?\s*$/,'').
|
|
19
|
+
gsub(/^\#{1,6}\s*/,'').
|
|
20
|
+
gsub(/(\*{1,2})(\S.*?\S)\1/,"\\2").
|
|
21
|
+
gsub(/(`{3,})(.*?)\1/m,"\\2").
|
|
22
|
+
gsub(/^-{3,}\s*$/,"").
|
|
23
|
+
gsub(/`(.+)`/,"\\1").
|
|
24
|
+
gsub(/\n{2,}/,"\n\n")
|
|
25
|
+
end
|
|
222
26
|
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
27
|
+
def strip_tags
|
|
28
|
+
return CGI.unescapeHTML(
|
|
29
|
+
gsub(/<(script|style|pre|code|figure).*?>.*?<\/\1>/im, '').
|
|
30
|
+
gsub(/<!--.*?-->/m, '').
|
|
31
|
+
gsub(/<(img|hr|br).*?>/i, " ").
|
|
32
|
+
gsub(/<(dd|a|h\d|p|small|b|i|blockquote|li)( [^>]*?)?>(.*?)<\/\1>/i, " \\3 ").
|
|
33
|
+
gsub(/<\/?(dt|a|ul|ol)( [^>]+)?>/i, " ").
|
|
34
|
+
gsub(/<[^>]+?>/, '').
|
|
35
|
+
gsub(/\[\d+\]/, '').
|
|
36
|
+
gsub(/’/,"'").gsub(/&.*?;/,' ').gsub(/;/,' ')
|
|
37
|
+
).lstrip.gsub("\xE2\x80\x98","'").gsub("\xE2\x80\x99","'").gsub("\xCA\xBC","'").gsub("\xE2\x80\x9C",'"').gsub("\xE2\x80\x9D",'"').gsub("\xCB\xAE",'"').squeeze(" ")
|
|
38
|
+
end
|
|
235
39
|
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
40
|
+
def strip_urls
|
|
41
|
+
gsub(/(https?:\/\/)?([\da-z\.-]+)\.([a-z\.]{2,6})([\/\w \.-]*)*\/?/i,"")
|
|
42
|
+
end
|
|
239
43
|
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
end
|
|
44
|
+
def strip_all
|
|
45
|
+
strip_tags.strip_markdown.strip
|
|
243
46
|
end
|
|
47
|
+
|
|
244
48
|
end
|
data/lib/jtag/version.rb
CHANGED
data/lib/jtag.rb
CHANGED
|
@@ -1,19 +1,13 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
require
|
|
4
|
-
require
|
|
5
|
-
require
|
|
6
|
-
require
|
|
7
|
-
require
|
|
8
|
-
require
|
|
9
|
-
require
|
|
10
|
-
require
|
|
11
|
-
require
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
require_relative "jtag/hash.rb"
|
|
15
|
-
require_relative "jtag/version.rb"
|
|
16
|
-
require_relative "jtag/string.rb"
|
|
17
|
-
require_relative "jtag/porter_stemming.rb"
|
|
18
|
-
require_relative "jtag/jekylltag.rb"
|
|
19
|
-
require_relative "jtag/util.rb"
|
|
1
|
+
require 'net/http'
|
|
2
|
+
require 'cgi'
|
|
3
|
+
require 'fileutils'
|
|
4
|
+
require 'yaml'
|
|
5
|
+
require 'csv'
|
|
6
|
+
require 'json'
|
|
7
|
+
require 'plist'
|
|
8
|
+
require 'jtag/version.rb'
|
|
9
|
+
require 'jtag/string.rb'
|
|
10
|
+
require 'jtag/porter_stemming.rb'
|
|
11
|
+
require 'jtag/jekylltag.rb'
|
|
12
|
+
require 'tmpdir'
|
|
13
|
+
require 'logger'
|
metadata
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: jtag
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.
|
|
4
|
+
version: 0.2.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Brett Terpstra
|
|
8
8
|
bindir: bin
|
|
9
9
|
cert_chain: []
|
|
10
|
-
date:
|
|
10
|
+
date: 1980-01-02 00:00:00.000000000 Z
|
|
11
11
|
dependencies:
|
|
12
12
|
- !ruby/object:Gem::Dependency
|
|
13
13
|
name: rake
|
|
@@ -55,14 +55,14 @@ dependencies:
|
|
|
55
55
|
name: gli
|
|
56
56
|
requirement: !ruby/object:Gem::Requirement
|
|
57
57
|
requirements:
|
|
58
|
-
- -
|
|
58
|
+
- - "~>"
|
|
59
59
|
- !ruby/object:Gem::Version
|
|
60
60
|
version: 2.20.0
|
|
61
61
|
type: :runtime
|
|
62
62
|
prerelease: false
|
|
63
63
|
version_requirements: !ruby/object:Gem::Requirement
|
|
64
64
|
requirements:
|
|
65
|
-
- -
|
|
65
|
+
- - "~>"
|
|
66
66
|
- !ruby/object:Gem::Version
|
|
67
67
|
version: 2.20.0
|
|
68
68
|
- !ruby/object:Gem::Dependency
|
|
@@ -93,6 +93,20 @@ dependencies:
|
|
|
93
93
|
- - ">="
|
|
94
94
|
- !ruby/object:Gem::Version
|
|
95
95
|
version: '0'
|
|
96
|
+
- !ruby/object:Gem::Dependency
|
|
97
|
+
name: ostruct
|
|
98
|
+
requirement: !ruby/object:Gem::Requirement
|
|
99
|
+
requirements:
|
|
100
|
+
- - ">="
|
|
101
|
+
- !ruby/object:Gem::Version
|
|
102
|
+
version: '0'
|
|
103
|
+
type: :runtime
|
|
104
|
+
prerelease: false
|
|
105
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
106
|
+
requirements:
|
|
107
|
+
- - ">="
|
|
108
|
+
- !ruby/object:Gem::Version
|
|
109
|
+
version: '0'
|
|
96
110
|
email: me@brettterpstra.com
|
|
97
111
|
executables:
|
|
98
112
|
- jtag
|
|
@@ -101,33 +115,18 @@ extra_rdoc_files:
|
|
|
101
115
|
- README.rdoc
|
|
102
116
|
- jtag.rdoc
|
|
103
117
|
files:
|
|
104
|
-
- ".irbrc"
|
|
105
|
-
- CHANGELOG.md
|
|
106
|
-
- Gemfile
|
|
107
|
-
- Jekyll/plugins/autotag_gen.rb
|
|
108
|
-
- Jekyll/source/_layouts/tags_json.html
|
|
109
|
-
- README.md
|
|
110
118
|
- README.rdoc
|
|
111
|
-
- Rakefile
|
|
112
119
|
- bin/jtag
|
|
113
|
-
- jtag.completion.bash
|
|
114
|
-
- jtag.gemspec
|
|
115
120
|
- jtag.rdoc
|
|
116
121
|
- lib/jtag.rb
|
|
117
|
-
- lib/jtag/array.rb
|
|
118
122
|
- lib/jtag/config_files/blacklist.txt
|
|
119
123
|
- lib/jtag/config_files/config.yml
|
|
120
124
|
- lib/jtag/config_files/stopwords.txt
|
|
121
125
|
- lib/jtag/config_files/synonyms.yml
|
|
122
|
-
- lib/jtag/errors.rb
|
|
123
|
-
- lib/jtag/hash.rb
|
|
124
126
|
- lib/jtag/jekylltag.rb
|
|
125
127
|
- lib/jtag/porter_stemming.rb
|
|
126
128
|
- lib/jtag/string.rb
|
|
127
|
-
- lib/jtag/stupid_json.rb
|
|
128
|
-
- lib/jtag/util.rb
|
|
129
129
|
- lib/jtag/version.rb
|
|
130
|
-
- mise.toml
|
|
131
130
|
homepage: http://brettterpstra.com
|
|
132
131
|
licenses: []
|
|
133
132
|
metadata: {}
|
|
@@ -150,7 +149,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
150
149
|
- !ruby/object:Gem::Version
|
|
151
150
|
version: '0'
|
|
152
151
|
requirements: []
|
|
153
|
-
rubygems_version: 3.6.
|
|
152
|
+
rubygems_version: 3.6.7
|
|
154
153
|
specification_version: 4
|
|
155
154
|
summary: Auto-tagging and tagging tools for Jekyll
|
|
156
155
|
test_files: []
|
data/.irbrc
DELETED
data/CHANGELOG.md
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
### 0.1.19
|
|
2
|
-
|
|
3
|
-
2024-09-16 13:15
|
|
4
|
-
|
|
5
|
-
#### NEW
|
|
6
|
-
|
|
7
|
-
- Allows piping of file lists. For actions to which it applies, you can pipe a file list, either from a previous jtag command or from another source (newline separated) to act on only those files, e.g. `jtag posts_tagged keyboard | jtag tags`
|
|
8
|
-
|
|
9
|
-
#### FIXED
|
|
10
|
-
|
|
11
|
-
- File.exists? => File.exist? for Ruby 3
|
|
12
|
-
|
|
13
|
-
### 1.0
|
|
14
|
-
|
|
15
|
-
Initial release
|
data/Gemfile
DELETED
|
@@ -1,58 +0,0 @@
|
|
|
1
|
-
#
|
|
2
|
-
# Author: Brett Terpstra
|
|
3
|
-
# Page generator for /data/tags.json, a list of all the tags on your blog and a list of the top 50 tags.
|
|
4
|
-
# Part of the AutoTag tool for Jekyll, but usable in other applications
|
|
5
|
-
#
|
|
6
|
-
# Looks for a tags_json.html template in your _layouts folder, see the example provided.
|
|
7
|
-
# Provides page.json_tags and page.json_tags_count as arrays for looping
|
|
8
|
-
#
|
|
9
|
-
# Config options for _config.yml
|
|
10
|
-
# tag_excludes: array of tags to exclude from all listings
|
|
11
|
-
# tags_json_dir: alternate of folder for the data.json file. Set to blank for root, defaults to 'data'
|
|
12
|
-
#
|
|
13
|
-
# If using tags.json with a javascript application, be sure you have the proper headers defined in .htaccess:
|
|
14
|
-
# AddType application/json json
|
|
15
|
-
# ExpiresByType application/json "access plus 0 seconds"
|
|
16
|
-
|
|
17
|
-
require 'json'
|
|
18
|
-
|
|
19
|
-
module Jekyll
|
|
20
|
-
|
|
21
|
-
class AutoTag < Page
|
|
22
|
-
def initialize(site, base, dir)
|
|
23
|
-
@site = site
|
|
24
|
-
@base = base
|
|
25
|
-
@dir = dir
|
|
26
|
-
@name = 'tags.json'
|
|
27
|
-
self.process(@name)
|
|
28
|
-
self.read_yaml(File.join(base, '_layouts'), 'tags_json.html')
|
|
29
|
-
tags_with_counts = site.tags.delete_if {|k,v|
|
|
30
|
-
site.config['tag_excludes'].include?(k) unless site.config['tag_excludes'].nil?
|
|
31
|
-
}.sort_by { |k,v| v.count }.reverse
|
|
32
|
-
|
|
33
|
-
self.data['json_tags'] = tags_with_counts.sort {|a,b| a[0].downcase <=> b[0].downcase }.map {|k,v| k }
|
|
34
|
-
self.data['json_tags_count'] = []
|
|
35
|
-
tags_with_counts.each { |k,v|
|
|
36
|
-
self.data['json_tags_count'] << {
|
|
37
|
-
"name" => k,
|
|
38
|
-
"count" => v.count
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
end
|
|
42
|
-
end
|
|
43
|
-
class AutoTagGenerator < Generator
|
|
44
|
-
safe true
|
|
45
|
-
def generate(site)
|
|
46
|
-
if site.layouts.key? 'tags_json'
|
|
47
|
-
dir = site.config['tag_json_dir'] || 'data'
|
|
48
|
-
write_tag_json(site, dir)
|
|
49
|
-
end
|
|
50
|
-
end
|
|
51
|
-
def write_tag_json(site, dir)
|
|
52
|
-
index = AutoTag.new(site, site.source, dir)
|
|
53
|
-
index.render(site.layouts, site.site_payload)
|
|
54
|
-
index.write(site.dest)
|
|
55
|
-
site.pages << index
|
|
56
|
-
end
|
|
57
|
-
end
|
|
58
|
-
end
|