Class: Jekyll::ID::Generator

Inherits:
Generator
  • Object
show all
Defined in:
lib/jekyll-id.rb

Constant Summary collapse

CONVERTER_CLASS =
Jekyll::Converters::Markdown
CONFIG_KEY =

config

"ids"
ENABLED_KEY =
"enabled"
EXCLUDE_KEY =
"exclude"
FORMAT_KEY =
"format"
ALPHA_KEY =
"alpha"
SIZE_KEY =
"size"

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(config) ⇒ Generator

Returns a new instance of Generator.



26
27
28
29
# File 'lib/jekyll-id.rb', line 26

def initialize(config)
  @config ||= config
  @testing ||= config['testing'].nil? ? false : config['testing']
end

Instance Attribute Details

#configObject (readonly)

for testing



15
16
17
# File 'lib/jekyll-id.rb', line 15

def config
  @config
end

Instance Method Details

#alphaObject

‘getters’



141
142
143
# File 'lib/jekyll-id.rb', line 141

def alpha
  return option_format(ALPHA_KEY).nil? ? '' : option_format(ALPHA_KEY)
end

#alpha_formatted?(id) ⇒ Boolean

descriptor methods

Returns:

  • (Boolean)


125
126
127
128
# File 'lib/jekyll-id.rb', line 125

def alpha_formatted?(id)
  return true if !option_format(ALPHA_KEY)
  return id.chars.all? { |char| alpha.include?(char) }
end

#disabled?Boolean

config helpers

Returns:

  • (Boolean)


151
152
153
# File 'lib/jekyll-id.rb', line 151

def disabled?
  option(ENABLED_KEY) == false
end

#exclude?(type) ⇒ Boolean

Returns:

  • (Boolean)


155
156
157
158
# File 'lib/jekyll-id.rb', line 155

def exclude?(type)
  return false unless option(EXCLUDE_KEY)
  return option(EXCLUDE_KEY).include?(type.to_s)
end

#generate(site) ⇒ Object



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
# File 'lib/jekyll-id.rb', line 31

def generate(site)
  return if disabled?

  @site = site
  @yesall = false
  @noall = false

  markdown_converter = site.find_converter_instance(CONVERTER_CLASS)
  # filter docs based on configs
  docs = []
  docs += site.docs_to_write.filter { |d| !exclude?(d.type) }
  @md_docs = docs.filter { |doc| markdown_converter.matches(doc.extname) }
  if @md_docs.nil? || @md_docs.empty?
    Jekyll.logger.warn("Jekyll-ID: No documents to process.")
  end

  @md_docs.each do |doc|
    prep_id(doc)
  end
end

#generate_idObject



83
84
85
86
87
88
89
90
# File 'lib/jekyll-id.rb', line 83

def generate_id
  has_size  = (size.size != 0)
  has_alpha = (alpha.size != 0)
  return Nanoid.generate                              if !strict?
  return Nanoid.generate(size: size, alphabet: alpha) if has_size && has_alpha
  return Nanoid.generate(size: size)                  if has_size && !has_alpha
  return Nanoid.generate(alphabet: alpha)             if !has_size && has_alpha
end

#option(key) ⇒ Object



160
161
162
# File 'lib/jekyll-id.rb', line 160

def option(key)
  @config[CONFIG_KEY] && @config[CONFIG_KEY][key]
end

#option_format(key) ⇒ Object



164
165
166
# File 'lib/jekyll-id.rb', line 164

def option_format(key)
  @config[CONFIG_KEY] && @config[CONFIG_KEY][FORMAT_KEY] && @config[CONFIG_KEY][FORMAT_KEY][key]
end

#prep_id(doc) ⇒ Object

helpers



54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
# File 'lib/jekyll-id.rb', line 54

def prep_id(doc)
  return if @noall
  has_id = doc.data.keys.include?('id')
  # 0   == is strict
  # nil == isn't strict
  is_strict_id = (alpha_formatted?(doc.data['id'].to_s) && size_formatted?(doc.data['id'].to_s))
  # cases where we would want to generate a new id
  case_1 = !has_id                   # no id exists
  case_2 = strict? && !is_strict_id  # id isn't formatted properly
  if (case_1 || case_2)
    new_id = generate_id.to_s 
    # populate missing id
    if case_1
      Jekyll.logger.info("\n> Generate frontmatter ID for \n> #{doc.inspect}\n>with new ID: '#{new_id}'")
    # replace invalid format id
    elsif case_2
      Jekyll.logger.info("\n> Replace frontmatter ID for:\n> #{doc.inspect}\n> from:'#{doc.data['id']}'\n> to:'#{new_id}'")
    # um...
    else
      Jekyll.logger.warn("Jekyll-ID: Invalid ID case")
    end
    resp = request if !@testing
    if @testing || ((@yesall || resp == "yes") && !@noall)
      write_id(doc, new_id)
      doc.data['id'] = new_id
    end
  end
end

#requestObject



92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
# File 'lib/jekyll-id.rb', line 92

def request
  if !@yesall && !@noall
    Jekyll.logger.info("\n> Is that ok?")
    Jekyll.logger.info("> (yes, no, yesall, or noall)")
    cont = gets
    if cont.strip == "yesall"
      @yesall = true
      Jekyll.logger.info("> Handle all IDs...")
    elsif cont.strip == "noall"
      @noall = true
      Jekyll.logger.info("> Leaving all IDs alone...")
    elsif cont.strip == "yes" 
      Jekyll.logger.info("> Handling ID...")
    elsif cont.strip == "no"
      Jekyll.logger.info("> Leaving ID alone...")
    else
      Jekyll.logger.error("Jekyll-ID: Invalid response. Skipping...")
    end
    return cont.strip
  end
end

#sizeObject



145
146
147
# File 'lib/jekyll-id.rb', line 145

def size
  return option_format(SIZE_KEY).nil? ? '' : option_format(SIZE_KEY)
end

#size_formatted?(id) ⇒ Boolean

Returns:

  • (Boolean)


130
131
132
133
# File 'lib/jekyll-id.rb', line 130

def size_formatted?(id)
  return true if !option_format(SIZE_KEY)
  return id.size == size
end

#strict?Boolean

Returns:

  • (Boolean)


135
136
137
# File 'lib/jekyll-id.rb', line 135

def strict?
  return option(FORMAT_KEY) && (option_format(SIZE_KEY) || option_format(ALPHA_KEY))
end

#write_id(doc, id) ⇒ Object



114
115
116
117
118
119
120
121
# File 'lib/jekyll-id.rb', line 114

def write_id(doc, id) 
  lines = IO.readlines(doc.path)
  lines.delete_if { |l| l.include?("id: #{doc.data['id']}") }
  lines.insert(1, "id: #{id}\n")
  File.open(doc.path, 'w') do |file|
    file.puts lines
  end
end