Top Level Namespace

Defined Under Namespace

Modules: ErrorChecks, PathSep Classes: RuneBlog

Constant Summary collapse

OpenStruct.new
Already_publish =
nil
Already_runeblog =
nil
LIVE =
"defined"
LEXT =
".lt3"

Instance Method Summary collapse

Instance Method Details

#_blank(url) ⇒ Object



908
909
910
911
# File 'lib/liveblog.rb', line 908

def _blank(url)
  log!(enter: __method__)
  %[href='#{url}' target='blank']
end

#_card_generic(card_title:, middle:, extra: "") ⇒ Object



882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
# File 'lib/liveblog.rb', line 882

def _card_generic(card_title:, middle:, extra: "")
  log!(enter: __method__)
  front = <<-HTML
    <div class="card #{extra} mb-3">
      <div class="card-body">
        <h5 class="card-title">#{card_title}</h5>
  HTML

  tail = <<-HTML
      </div>
    </div>
  HTML
  text = front + middle + tail
  api.out text + "\n "
end

#_errout(*args) ⇒ Object



826
827
828
829
# File 'lib/liveblog.rb', line 826

def _errout(*args)
  log!(enter: __method__)
  ::STDERR.puts *args
end

#_get_data(file) ⇒ Object



38
39
40
41
42
43
44
45
46
47
# File 'lib/lowlevel.rb', line 38

def _get_data(file)
  log!(enter: __method__, args: [file], level: 2)
  lines = File.readlines(file)
  lines = lines.map do |line|
    line = line.chomp.strip
    line.sub(/ *# .*$/, "")    # allow leading/trailing comments
  end
  lines.reject! {|x| x.empty? }
  lines
end

#_get_data?(file) ⇒ Boolean

File need not exist

Returns:

  • (Boolean)


33
34
35
36
# File 'lib/lowlevel.rb', line 33

def _get_data?(file)   # File need not exist
  log!(enter: __method__, args: [file], level: 2)
  File.exist?(file) ? _get_data(file) : []
end

#_got_python?Boolean

Returns:

  • (Boolean)


68
69
70
71
72
73
74
# File 'lib/liveblog.rb', line 68

def _got_python?
  log!(enter: __method__)
  # Dumb - fix later - check up front as needed
  # Should also check for praw lib
  str = `which python3`
  str.length > 0
end

#_handle_standard_widget(tag) ⇒ Object



612
613
614
615
616
617
618
619
620
621
622
# File 'lib/liveblog.rb', line 612

def _handle_standard_widget(tag)
  log!(enter: __method__)
  wtag = "../../widgets"/tag
  code = _load_local(tag)
  if code 
    Dir.chdir(wtag) do 
      widget = code.new(@blog)
      widget.build
    end
  end
end

#_html_body(file, css = nil) ⇒ Object

helper methods



813
814
815
816
817
818
819
820
821
822
823
824
# File 'lib/liveblog.rb', line 813

def _html_body(file, css = nil)
  log!(enter: __method__)
  file.puts "<html>"
  if css
    file.puts "    <head>"  
    file.puts "        <style>\n#{css}\n          </style>"
    file.puts "    </head>"  
  end
  file.puts "  <body>"
  yield
  file.puts "  </body>\n</html>"
end

#_load_local(widget) ⇒ Object



597
598
599
600
601
602
603
604
605
606
607
608
609
610
# File 'lib/liveblog.rb', line 597

def _load_local(widget)
  log!(enter: __method__)
  Dir.chdir("../../widgets/#{widget}") do
    rclass = _make_class_name(widget)
    found = (require("./#{widget}") if File.exist?("#{widget}.rb"))
    code = found ? ::RuneBlog::Widget.class_eval(rclass) : nil
    code
  end
rescue => err
  STDERR.puts err.to_s
  STDERR.puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
  sleep 6; RubyText.stop
  exit
end

#_main(url) ⇒ Object



903
904
905
906
# File 'lib/liveblog.rb', line 903

def _main(url)
  log!(enter: __method__)
  %[href="javascript: void(0)" onclick="javascript:open_main('#{url}')"]
end

#_make_class_name(app) ⇒ Object



586
587
588
589
590
591
592
593
594
595
# File 'lib/liveblog.rb', line 586

def _make_class_name(app)
  log!(enter: __method__)
  if app =~ /[-_]/
    words = app.split(/[-_]/)
    name = words.map(&:capitalize).join
  else
    name = app.capitalize
  end
  return name
end

#_make_navbar(orient = :horiz) ⇒ Object



757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
# File 'lib/liveblog.rb', line 757

def _make_navbar(orient = :horiz)
  log!(enter: __method__)
  vdir = @root/:views/@blog.view
  title = _var("view.title")

  if orient == :horiz
    name = "navbar.html"
    li1, li2 = "", ""
    extra = "navbar-expand-lg" 
    list1 = list2 = ""
  else
    name = "vnavbar.html"
    li1, li2 = '<li class="nav-item">', "</li>"
    extra = ""
    list1, list2 = '<l class="navbar-nav mr-auto">', "</ul>"
  end
  
  start = <<-HTML
   <table><tr><td>
   <nav class="navbar #{extra} navbar-light bg-light">
      #{list1}
  HTML
  finish = <<-HTML
      #{list2}
    </nav>
    </td></tr></table>
  HTML

  html_file = @blog.root/:views/@blog.view/"themes/standard/banner/navbar"/name
  output = File.new(html_file, "w")
  output.puts start
  lines = _read_navbar_data
  lines = ["index  Home"] + lines  unless api.args.include?("nohome")
  lines.each do |line|
    basename, cdata = line.chomp.strip.split(" ", 2)
    full = :banner/:navbar/basename+".html"
    href_main = _main(full)
    if basename == "index"  # special case
      output.puts %[#{li1} <a class="nav-link" href="index.html">#{cdata}<span class="sr-only">(current)</span></a> #{li2}]
    else
      dir = @blog.root/:views/@blog.view/"themes/standard/banner/navbar"
      dest = vdir/"remote/banner/navbar"/basename+".html"
      preprocess cwd: dir, src: basename, dst: dest, call: ".nopara", vars: @blog.view.globals # , debug: true
      output.puts %[#{li1} <a class="nav-link" #{href_main}>#{cdata}</a> #{li2}]
    end
  end
  output.puts finish
  output.close
  return File.read(html_file)
end

#_passthru(line) ⇒ Object



831
832
833
834
835
836
837
# File 'lib/liveblog.rb', line 831

def _passthru(line)
  log!(enter: __method__)
  return if line.nil?
  line = _format(line)
  api.out line + "\n"
  api.out "<p>" if line.empty? && ! @_nopara
end

#_passthru_noline(line) ⇒ Object



839
840
841
842
843
844
845
# File 'lib/liveblog.rb', line 839

def _passthru_noline(line)
  log!(enter: __method__)
  return if line.nil?
  line = _format(line)
  api.out line
  api.out "<p>" if line.empty? && ! @_nopara
end

#_post_lookup(postid) ⇒ Object

side-effect



857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
# File 'lib/liveblog.rb', line 857

def _post_lookup(postid)    # side-effect
  log!(enter: __method__)
  # .. = templates, ../.. = views/thisview
  slug = title = date = teaser_text = nil

  view = @blog.view
  vdir = view.dir rescue "NONAME"
  setvar("View", view.name)
  setvar("ViewDir", @blog.root/:views/view.name)
tmp = File.new("/tmp/PL-#{Time.now.to_i}.txt", "w")
tmp.puts "_post_lookup: blog.view = #{@blog.view.inspect}"
tmp.puts "_post_lookup: vdir = #{vdir}"
  dir_posts = @vdir/:posts
  posts = Dir.entries(dir_posts).grep(/^\d\d\d\d/).map {|x| dir_posts/x }
  posts.select! {|x| File.directory?(x) }

tmp.puts "_post_lookup: postid = #{postid}"
tmp.puts "_post_lookup: posts  = \n#{posts.inspect}"
tmp.close
  posts = posts.select {|x| File.basename(x).to_i == postid }
  postdir = exactly_one(posts, posts.inspect)
  vp = RuneBlog::ViewPost.new(@blog.view, postdir)
  vp
end

#_read_navbar_dataObject



177
178
179
180
181
182
183
# File 'lib/liveblog.rb', line 177

def _read_navbar_data
  log!(enter: __method__)
  vdir = @blog.root/:views/@blog.view
  dir = vdir/"themes/standard/banner/navbar/"
  datafile = dir/"list.data"
  _get_data(datafile)
end

#_reddit_post_url(vdir, date, title, url) ⇒ Object



76
77
78
79
80
81
82
83
84
85
86
87
88
# File 'lib/liveblog.rb', line 76

def _reddit_post_url(vdir, date, title, url)
  log!(enter: __method__)
  _got_python?
  tmpfile = "/tmp/reddit-post-url.txt"
  File.open(tmpfile, "w") do |tmp|
    tmp.puts "[#{date}]  #{title}"
    tmp.puts url
  end
  rid = nil
  Dir.chdir(vdir/:config) { rid = `python3 reddit/reddit_post_url.py` }
  system("rm #{tmpfile}")
  rid  # returns reddit id
end

#_svg_title(*args) ⇒ Object



250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
# File 'lib/liveblog.rb', line 250

def _svg_title(*args)
  log!(enter: __method__)
  width    = "95%"
  height   = 90
  bgcolor  = "black"
  style    = nil
  size     = ""
  font     = "sans-serif"
  color    = "white"
  xy       = "5,5"
  align    = "center"
  style2   = nil
  size2    = ""
  font2    = "sans-serif"
  color2   = "white"
  xy2      = "5,5"
  align2   = "center"

  e = args.each
  hash = {}  # TODO get rid of hash??

  valid = %w[width height bgcolor style size font color xy 
             align style2 size2 font2 color2 xy2 align2]
  os = OpenStruct.new
  loop do
    arg = e.next
    arg = arg.chop
    raise "Don't know '#{arg}'" unless valid.include?(arg)
    os.send(arg+"=", e.next)
  end
  x, y = xy.split(",")
  x2, y2 = xy2.split(",")
  names = %w[x y x2 y2] + valid
  names.each {|name| hash[name] = os.send(name) }
  result = <<~HTML
    <svg width="#{width}" height="#{height}"
         viewBox="0 0 #{width} #{height}">
      <defs>
        <linearGradient id="grad1" x1="100%" y1="100%" x2="0%" y2="100%">
          <stop offset="0%" style="stop-color:rgb(198,198,228);stop-opacity:1" />
          <stop offset="100%" style="stop-color:rgb(30,30,50);stop-opacity:1" />
        </linearGradient>
      </defs>
      <style>
        .title    { font: #{style} #{size} #{font}; fill: #{color} }
        .subtitle { font: #{style2} #{size2} #{font2}; fill: #{color2} }
      </style>
      <rect x="10" y="10" rx="10" ry="10" width="#{width}" height="#{height}" fill="url(#grad1)"/>
      <text text-anchor="#{align}"  x="#{x}" y="#{y}" class="title">#{Livetext::Vars["view.title"]} </text>
      <text text-anchor="#{align2}" x="#{x2}" y="#{y2}" class="subtitle">#{Livetext::Vars["view.subtitle"]} </text>
    </svg> 
    <!-- ^ how does syntax highlighting get messed up? </svg> -->
  HTML
  [result, hash]
end

#_tmp_error(err) ⇒ Object



2
3
4
5
6
7
# File 'lib/lowlevel.rb', line 2

def _tmp_error(err)
  STDERR.puts err
  STDERR.puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
  log!(str: "#{err} - see also stderr.out")
  log!(str: err.backtrace.join("\n")) if err.respond_to?(:backtrace)
end

#_var(name) ⇒ Object

FIXME scope issue!



898
899
900
901
# File 'lib/liveblog.rb', line 898

def _var(name)  # FIXME scope issue!
  log!(enter: __method__)
  ::Livetext::Vars[name] || "[:#{name} is undefined]"
end

#_write_metadataObject



847
848
849
850
851
852
853
854
855
# File 'lib/liveblog.rb', line 847

def 
  log!(enter: __method__)
  File.write("teaser.txt", @meta.teaser)
  fields = [:num, :title, :date, :pubdate, :views, :tags, :pinned]
  fname = "metadata.txt"
  File.open(fname, "w") do |f| 
    fields.each {|fld| f.puts "#{'%8s' % fld}  #{@meta.send(fld)}" }
  end
end

#add_tagsObject



41
42
43
# File 'lib/newpost.rb', line 41

def add_tags
  puts __method__
end

#add_viewsObject



37
38
39
# File 'lib/newpost.rb', line 37

def add_views
  puts __method__
end

#addvar(vars, hash) ⇒ Object



132
133
134
135
136
137
138
# File 'lib/lowlevel.rb', line 132

def addvar(vars, hash)
  hash.each_pair do |k, v| 
    vars[k.to_s] = v
    vars[k.to_sym] = v
  end
  vars
end

#ask(prompt) ⇒ Object

Idea: A special sub-environment for creating a post

1. Display: view, post number, date
2. Menu?
3.   - Edit/enter title
4.   - Edit teaser
5.   - Add views
6.   - Add tags
7.   - Import assets
8.   - Save 
9.  - Quit

Edit body after save/quit



18
19
20
21
22
23
# File 'lib/newpost.rb', line 18

def ask(prompt)  # elsewhere?
  print prompt
  str = gets
  str.chomp! if str
  str
end


166
167
168
169
# File 'lib/liveblog.rb', line 166

def backlink
  log!(enter: __method__)
  api.out %[<br><a href="javascript:history.go(-1)">[Back]</a>]
end


185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
# File 'lib/liveblog.rb', line 185

def banner
  log!(enter: __method__)
  count = 0
  bg = "white"  # outside loop
  wide = nil
  high = 250
  str2 = ""
  navbar = nil
  vdir = @blog.root/:views/@blog.view
  lines = api.body.to_a

  lines.each do |line|
    count += 1
    tag, *data = line.split
    data ||= []
    deps = [@blog.view.globals[:ViewDir]/:data/"global.lt3"]
    case tag
      when "width";   wide = data[0]
      when "height";  high = data[0]
      when "bgcolor"; bg = data[0] || "white"
      when "image"
        image = data[0] || "banner.jpg"
        image = "banner"/image
        wide = data[0]
        width = wide ? "width=#{wide}" : "" 
        str2 << "      <td><img src=#{image} #{width} height=#{high}></img></td>" + "\n"
      when "svg_title"
        stuff, hash = _svg_title(*data)
        wide = hash["width"]
        str2 << "      <td width=#{wide}>#{stuff}</td>" + "\n"
      when "text"
        data[0] ||= "top.html"
        file = "banner"/data[0]
        if ! File.exist?(file) 
          src = file.sub(/html$/, "lt3")
          if File.exist?(src)
            preprocess src: src, dst: file, deps: deps, call: ".nopara", vars: @blog.view.globals
          else
            raise FoundNeither(file, src)
          end
        end
        str2 << "<td>" + File.read(file) + "</td>" + "\n"
      when "navbar"
        navbar = _make_navbar  # horiz is default
      when "vnavbar"
        navbar = _make_navbar(:vert)
      when "break"
         str2 << "  </tr>\n  <tr>"  + "\n"
    else
      str2 << "        '#{tag}' isn't known" + "\n"
    end
  end
  api.out <<~HTML
    <table width=100% bgcolor=#{bg}>
      <tr>
        #{str2}
      </tr>
    </table>
  HTML
  api.out navbar if navbar
rescue => err
  STDERR.puts "err = #{err}"
  STDERR.puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
end

#categoriesObject

does nothing right now



314
315
316
# File 'lib/liveblog.rb', line 314

def categories   # does nothing right now
  log!(enter: __method__)
end

#codeObject



171
172
173
174
175
# File 'lib/liveblog.rb', line 171

def code
  log!(enter: __method__)
  lines = api.body # _text
  api.out "<font size=+1><pre>\n#{lines}\n</pre></font>"
end

#copy(src, dst) ⇒ Object



73
74
75
76
77
# File 'lib/lowlevel.rb', line 73

def copy(src, dst)
  log!(enter: __method__, args: [src, dst], level: 2)
  cmd = "cp #{src} #{dst} 2>/dev/null"
  system!(cmd)
end

#copy!(src, dst) ⇒ Object



79
80
81
82
83
# File 'lib/lowlevel.rb', line 79

def copy!(src, dst)
  log!(enter: __method__, args: [src, dst], level: 2)
  cmd = "cp -r #{src} #{dst} 2>/dev/null"
  system!(cmd)
end

#create_dirs(*dirs) ⇒ Object



85
86
87
88
89
90
91
92
93
94
# File 'lib/lowlevel.rb', line 85

def create_dirs(*dirs)
  log!(enter: __method__, args: [*dirs], level: 3)
  dirs.each do |dir|
    dir = dir.to_s  # symbols allowed
    next if Dir.exist?(dir)
    cmd = "mkdir -p #{dir} >/dev/null"
    result = system!(cmd) 
    raise CantCreateDir(dir) unless result
  end
end

#dropcapObject

“dot” commands



49
50
51
52
53
54
55
56
57
58
# File 'lib/liveblog.rb', line 49

def dropcap
  log!(enter: __method__)
  # Bad form: adds another HEAD
  text = api.data
  api.out " "
  letter = text[0]
  remain = text[1..-1]
  api.out %[<div class='mydrop'>#{letter}</div>]
  api.out %[<div style="padding-top: 1px">#{remain}]
end

#dump(obj, name) ⇒ Object



9
10
11
# File 'lib/lowlevel.rb', line 9

def dump(obj, name)
  File.write(name, obj)
end

#edit(str) ⇒ Object



8
9
10
# File 'lib/menus.rb', line 8

def edit(str)
  proc { edit_file(str) }
end

#edit_blog_bannerObject



33
34
35
# File 'lib/menus.rb', line 33

def edit_blog_banner
  edit_file("#@std/banner/banner.lt3")
end

#edit_blog_generateObject



17
18
19
# File 'lib/menus.rb', line 17

def edit_blog_generate
  edit_file("#@std/blog/generate.lt3")
end

#edit_blog_headObject



21
22
23
# File 'lib/menus.rb', line 21

def edit_blog_head
  edit_file("#@std/blog/head.lt3")
end

#edit_blog_indexObject



25
26
27
# File 'lib/menus.rb', line 25

def edit_blog_index
  edit_file("#@std/blog/index.lt3")
end

#edit_blog_navbarObject



37
38
39
# File 'lib/menus.rb', line 37

def edit_blog_navbar
  edit_file("#@std/navbar/navbar.lt3")
end

#edit_config_facebookObject



77
78
79
# File 'lib/menus.rb', line 77

def edit_config_facebook
  edit_file("config/facebook/credentials.txt")
end

#edit_config_redditObject



73
74
75
# File 'lib/menus.rb', line 73

def edit_config_reddit
  edit_file("config/reddit/credentials.txt")
end

#edit_config_twitterObject



81
82
83
# File 'lib/menus.rb', line 81

def edit_config_twitter
  edit_file("config/twitter/credentials.txt")
end

#edit_etc_blog_cssObject



85
86
87
# File 'lib/menus.rb', line 85

def edit_etc_blog_css
  edit_file("#@std/etc/blog.css.lt3")
end

#edit_etc_externalsObject



89
90
91
# File 'lib/menus.rb', line 89

def edit_etc_externals
  edit_file("#@std/etc/externals.lt3") 
end

#edit_post_entryObject



29
30
31
# File 'lib/menus.rb', line 29

def edit_post_entry
  edit_file("#@std/blog/post_entry.lt3")
end

#edit_post_generateObject



41
42
43
# File 'lib/menus.rb', line 41

def edit_post_generate
  edit_file("#@std/post/generate.lt3")
end

#edit_post_headObject



45
46
47
# File 'lib/menus.rb', line 45

def edit_post_head
  edit_file("#@std/post/head.lt3")
end

#edit_post_indexObject



49
50
51
# File 'lib/menus.rb', line 49

def edit_post_index
  edit_file("#@std/post/index.lt3")
end

#edit_settings_featuresObject



69
70
71
# File 'lib/menus.rb', line 69

def edit_settings_features
  edit_file("settings/features.txt")
end

#edit_settings_publishObject



65
66
67
# File 'lib/menus.rb', line 65

def edit_settings_publish
  edit_file("settings/publish.txt")
end

#edit_settings_recentObject



61
62
63
# File 'lib/menus.rb', line 61

def edit_settings_recent
  edit_file("settings/recent.txt")
end

#edit_settings_viewObject



57
58
59
# File 'lib/menus.rb', line 57

def edit_settings_view
  edit_file("settings/view.txt")
end

#edit_teaserObject



31
32
33
34
35
# File 'lib/newpost.rb', line 31

def edit_teaser
  puts __method__
  str = ask("Teaser:   ")
  puts str.inspect
end

#edit_view_globalObject



53
54
55
# File 'lib/menus.rb', line 53

def edit_view_global
  edit_file("#@data/global.lt3")
end

#enter_titleObject



25
26
27
28
29
# File 'lib/newpost.rb', line 25

def enter_title
  puts __method__
  str = ask("Title:    ")
  puts str.inspect
end

#error(err) ⇒ Object



102
103
104
105
106
107
# File 'lib/lowlevel.rb', line 102

def error(err)
  log!(str: err, enter: __method__, args: [err], level: 2)
  str = "\n  Error... #{err}"
  puts str
  puts err.backtrace.join("\n")
end

#exactly_one(list, tag = nil, &block) ⇒ Object



124
125
126
127
128
129
130
# File 'lib/lowlevel.rb', line 124

def exactly_one(list, tag = nil, &block)
  log!(enter: __method__, args: [list], level: 2)
  list2 = list.select(&block)
  raise "List: Zero instances #{"- #{tag}" if tag}" if list.empty?
  raise "List: More than one instance #{"- #{tag}" if tag}" if list.size > 1
  list.first
end

#faqObject



151
152
153
154
155
156
157
158
159
160
161
162
163
164
# File 'lib/liveblog.rb', line 151

def faq
  log!(enter: __method__)
  @faq_count ||= 0
  api.out "<br>" if @faq_count == 0
  @faq_count += 1
  ques = api.data.chomp
  ans  = api.body.join("\n")
  id = "faq#@faq_count"
  api.out %[&nbsp;<a data-toggle="collapse" href="##{id}" role="button" aria-expanded="false" aria-controls="collapseExample"><font size=+3>&#8964;</font></a>]
  api.out %[&nbsp;<b>#{ques}</b>]
  api.out %[<div class="collapse" id="#{id}"><br><font size=+1>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#{ans}</font></div>\n]
  api.out "<br>" # unless @faq_count == 1
  api.optional_blank_line
end

#finalizeObject



487
488
489
490
491
492
493
494
495
496
497
# File 'lib/liveblog.rb', line 487

def finalize
  log!(str: "Now exiting livetext processing...")
  return unless @meta
  return @meta if @blog.nil?

  @slug = @blog.make_slug(@meta)
  slug_dir = @slug
  @postdir = @blog.view.dir/:posts/slug_dir
  write_post
  @meta
end

#find_item(list, &block) ⇒ Object



109
110
111
112
113
# File 'lib/lowlevel.rb', line 109

def find_item(list, &block)
  log!(enter: __method__, args: [list], level: 2)
  list2 = list.select(&block)
  exactly_one(list2, list.join("/"))
end

#find_item!(list, &block) ⇒ Object



115
116
117
118
119
120
121
122
# File 'lib/lowlevel.rb', line 115

def find_item!(list, &block)
  log!(enter: __method__, args: [list], level: 2)
  list2 = list.select(&block)
  list2 = list.select(&block)
  item = exactly_one(list2, list.join("/"))
  n = list.index(&block)
  [n, item]
end

#get_live_vars(src) ⇒ Object



79
80
81
82
83
84
85
86
87
88
# File 'lib/processing.rb', line 79

def get_live_vars(src)
  dir, base = File.dirname(src), File.basename(src)
  live = Livetext.customize(call: [".nopara"])
  Dir.chdir(dir) { live.xform_file(base) }
  live
rescue => e
  puts e
  puts $!
  gets
end

#h1Object

Move elsewhere later!



326
# File 'lib/liveblog.rb', line 326

def h1; _passthru "<h1>#{@_data}</h1>"; end

#h2Object



327
# File 'lib/liveblog.rb', line 327

def h2; _passthru "<h2>#{@_data}</h2>"; end

#h3Object



328
# File 'lib/liveblog.rb', line 328

def h3; _passthru "<h3>#{@_data}</h3>"; end

#h4Object



329
# File 'lib/liveblog.rb', line 329

def h4; _passthru "<h4>#{@_data}</h4>"; end

#h5Object



330
# File 'lib/liveblog.rb', line 330

def h5; _passthru "<h5>#{@_data}</h5>"; end

#h6Object



331
# File 'lib/liveblog.rb', line 331

def h6; _passthru "<h6>#{@_data}</h6>"; end

#headObject

Does NOT output <head> tags



499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
# File 'lib/liveblog.rb', line 499

def head  # Does NOT output <head> tags
  log!(enter: __method__)
  args = api.args
  args.each do |inc|
    self.data = inc
    dot_include
  end
  # Depends on vars: title, desc, host
  defaults = {}
  defaults = { "charset"        => %[<meta charset="utf-8">],
               "http-equiv"     => %[<meta http-equiv="X-UA-Compatible" content="IE=edge">],
               "title"          => %[<title>\n  #{_var("view.title")} | #{_var("view.subtitle")}\n  </title>],
               "generator"      => %[<meta name="generator" content="Runeblog v #@version">],
               "og:title"       => %[<meta property="og:title" content="#{_var("view.title")}">],
               "og:locale"      => %[<meta property="og:locale" content="#{_var(:locale)}">],
               "description"    => %[<meta name="description" content="#{_var("view.subtitle")}">],
               "og:description" => %[<meta property="og:description" content="#{_var("view.subtitle")}">],
               "linkc"          => %[<link rel="canonical" href="#{_var(:host)}">],
               "og:url"         => %[<meta property="og:url" content="#{_var(:host)}">],
               "og:site_name"   => %[<meta property="og:site_name" content="#{_var("view.title")}">],
#              "style"          => %[<link rel="stylesheet" href="etc/blog.css">],
# ^ FIXME
               "feed"           => %[<link type="application/atom+xml" rel="alternate" href="#{_var(:host)}/feed.xml" title="#{_var("view.title")}">],
               "favicon"        => %[<link rel="shortcut icon" type="image/x-icon" href="etc/favicon.ico">\n <link rel="apple-touch-icon" href="etc/favicon.ico">]
             }
  result = {}
  lines = api.body
  lines.each do |line|
    line.chomp
    word, remain = line.split(" ", 2)
    case word
      when "viewport"
        result["viewport"] = %[<meta name="viewport" content="#{remain}">]
      when "script"  # FIXME this is broken
        file = remain
        text = File.read(file)
        result["script"] = Livetext.new.transform(text)
      when "style"
        result["style"] = %[<link rel="stylesheet" href="etc/#{remain}">]
      # Later: allow other overrides
      when ""; break
    else
      if defaults[word]
        result[word] = %[<meta property="#{word}" content="#{remain}">]
      else
        puts "Unknown tag '#{word}'"
      end
    end
  end
  hash = defaults.dup.update(result)  # FIXME collisions?

  hash.each_value {|x| api.out "  " + x }
end

#hnavbarObject



747
748
749
750
# File 'lib/liveblog.rb', line 747

def hnavbar
  log!(enter: __method__)
  str = _make_navbar  # horiz is default
end

#hrObject



333
# File 'lib/liveblog.rb', line 333

def hr; _passthru "<hr>"; end

#import_assetsObject



45
46
47
# File 'lib/newpost.rb', line 45

def import_assets
  puts __method__
end

#init_liveblogObject

FIXME - a lot of this logic sucks



14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
# File 'lib/liveblog.rb', line 14

def init_liveblog    # FIXME - a lot of this logic sucks
  log!(enter: __method__)
  dir = Dir.pwd.sub(/\.blogs.*/, "")
  @blog = nil
  Dir.chdir(dir) { @blog = RuneBlog.new }
  @root = @blog.root
  @view = @blog.view
  @view_name = @blog.view.name unless @view.nil?
  @vdir = @blog.view.dir rescue "NONAME"
  setvar("View", @view_name)
  setvar("ViewDir", @blog.root/:views/@view_name)
  @version = RuneBlog::VERSION
  @theme = @vdir/:themes/:standard

  @reddit_comments = ""
  @reddit_enabled = @blog.features["reddit"]
  if @reddit_enabled
    @reddit_comments = <<~HTML
      <a href="#reddit_comments">
        <img src="assets/reddit-logo.png" 
             width=24 height=24
             alt="Scroll to reddit comments"></img>
      </a>
    HTML
  end
  log!(str: "End of init_liveblog")
rescue => err
  STDERR.puts "err = #{err}"
  STDERR.puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
end

#insetObject

inset



370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
# File 'lib/liveblog.rb', line 370

def inset
  log!(enter: __method__)
  lines = api.body
  box = ""
  output = []
  lines.each do |line| 
    line = line
    case line[0]
      when "/"  # Only into inset
        line[0] = ' '
        box << line
        line.replace(" ")
      when "|"  # Into inset and body
        line[0] = ' '
        box << line
        output << line
    else  # Only into body
      output << line 
    end
  end
  lr = api.args.first
  wide = api.args[1] || "25"
  stuff = "<div style='float:#{lr}; width: #{wide}%; padding:8px; padding-right:12px'>"
  stuff << '<b><i>' + box + '</i></b></div>'
  api.out "</p>"   #  kludge!! nopara
  0.upto(2) {|i| _passthru output[i] }
  _passthru stuff
  3.upto(output.length-1) {|i| _passthru output[i] }
  api.out "<p>"  #  kludge!! para
  api.optional_blank_line
end

#interpolate(str, bind) ⇒ Object



96
97
98
99
100
# File 'lib/lowlevel.rb', line 96

def interpolate(str, bind)
  log!(enter: __method__, args: [str, bind], level: 3)
  wrap = "<<-EOS\n#{str}\nEOS"
  eval wrap, bind
end

#listObject



343
344
345
346
347
348
349
# File 'lib/liveblog.rb', line 343

def list
  log!(enter: __method__)
  api.out "<ul>"
  api.body {|line| api.out "<li>#{line}</li>" }
  api.out "</ul>"
  api.optional_blank_line
end

#list!Object



351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
# File 'lib/liveblog.rb', line 351

def list!
  log!(enter: __method__)
  api.out "<ul>"
  lines = api.body.each 
  loop do 
    line = lines.next
    line = api.format(line)
    if line[0] == " "
      api.out line
    else
      api.out "<li>#{line}</li>"
    end
  end
  api.out "</ul>"
  api.optional_blank_line
end

#log!(str: "", enter: nil, args: [], pwd: false, dir: false, level: 0, stderr: false) ⇒ Object



10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
# File 'lib/logging.rb', line 10

def log!(str: "", enter: nil, args: [], pwd: false, dir: false, level: 0, stderr: false)
  return unless $logging
  @err_level ||= ENV['RUNEBLOG_ERROR_LEVEL']
  @err_level ||= 0
  return if level < @err_level 

  time = Time.now.strftime("%H:%M:%S")

  meth = ""
  meth = "#{enter}" if enter

  para = "(#{args.inspect[1..-2]})"

  source = caller[0].sub(/.*\//, " in ").sub(/:/, " line ").sub(/:.*/, "")
  source = "in #{source} (probably liveblog.rb)" if source.include? "(eval)"

  str = "  ... #{str}" unless str.empty?
  indent = " "*12

  outlog "#{time} #{meth}#{para}"
  outlog "#{indent} #{str} " unless str.empty?
  outlog "#{indent} #{source}"
  outlog "#{indent} pwd = #{Dir.pwd} " if pwd
  if dir
    files = (Dir.entries('.') - %w[. ..]).join(" ")
    outlog "#{indent} dir/* = #{files}"
  end
#   outlog "#{indent} livetext params = #{livedata.inpect} " unless livedata.nil?
  outlog 
  $log.close
  $log = File.new("/tmp/runeblog.log","a")
end

#make_exception(sym, str, target_class = Object) ⇒ Object



2
3
4
5
6
7
8
9
10
11
# File 'lib/exceptions.rb', line 2

def make_exception(sym, str, target_class = Object)
  return if target_class.constants.include?(sym)

  target_class.const_set(sym, StandardError.dup)
  define_method(sym) do |*args|
    msg = str.dup
    args.each.with_index {|arg, i| msg.sub!("%#{i+1}", arg) }
    target_class.class_eval(sym.to_s).new(msg)
  end
end

#metaObject

newer stuff…



555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
# File 'lib/liveblog.rb', line 555

def meta
  log!(enter: __method__)
  args = api.args
  enum = args.each
  str = "<meta"
  arg = enum.next
  loop do 
    if arg.end_with?(":")
      str << " " << arg[0..-2] << "="
      a2 = enum.next
      str << %["#{a2}"]
    else
      STDERR.puts "=== meta error?"
    end
    arg = enum.next
  end
  str << ">"
  api.out str
end


752
753
754
755
# File 'lib/liveblog.rb', line 752

def navbar
  log!(enter: __method__)
  str = _make_navbar  # horiz is default
end

#newer?(f1, f2) ⇒ Boolean

Returns:

  • (Boolean)


8
9
10
# File 'lib/processing.rb', line 8

def newer?(f1, f2)
  File.mtime(f1) > File.mtime(f2)
end

#nlistObject



335
336
337
338
339
340
341
# File 'lib/liveblog.rb', line 335

def nlist
  log!(enter: api._method__)
  api.out "<ol>"
  api.body {|line| api.out "<li>#{line}</li>" }
  api.out "</ol>"
  api.optional_blank_line
end

#outlog(str = "", stderr: false) ⇒ Object



5
6
7
8
# File 'lib/logging.rb', line 5

def outlog(str = "", stderr: false)
  $log.puts str
  STDERR.puts str if stderr
end

#pinObject



441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
# File 'lib/liveblog.rb', line 441

def pin
  log!(enter: __method__)
  raise NoPostCall unless @meta
  api.debug "data = #{_args}"  # verify only valid views?
  pinned = @_args
  @meta.pinned = pinned
  pinned.each do |pinview|
    dir = @blog.root/:views/pinview/"widgets/pinned/"
    datafile = dir/"list.data"
    pins = _get_data?(datafile)
    pins << "#{@meta.num} #{@meta.title}\n"
    pins.uniq!
    File.open(datafile, "w") {|out| pins.each {|pin| out.puts pin } }
  end
  api.optional_blank_line
rescue => err
  STDERR.puts "err = #{err}"
  STDERR.puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
end

#postObject



60
61
62
63
64
65
66
# File 'lib/liveblog.rb', line 60

def post
  log!(enter: __method__)
  @meta = OpenStruct.new
  @meta.num = api.args[0]
  setvar("post.num", @meta.num.to_i)
  api.out "  <!-- Post number #{@meta.num} -->\n "
end

#post_toolbarObject



90
91
92
93
94
95
96
97
# File 'lib/liveblog.rb', line 90

def post_toolbar
  log!(enter: __method__)
  back_icon = %[<img src="assets/back-icon.png" width=24 height=24 alt="Go back"></img>]
  back = %[<a style="text-decoration: none" href="javascript:history.go(-1)">#{back_icon}</a>]
  api.out <<~HTML
    <div align='right'>#{back} #@reddit_comments</div>
  HTML
end

#post_trailerObject



99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
# File 'lib/liveblog.rb', line 99

def post_trailer
  log!(enter: __method__)
  # Not called from *inside* a post, therefore no @meta --
  # can/must call read_metadata
  num = _var("post.num").to_i
log! str:  "post_trailer: num = #{num}"
  vp = _post_lookup(num)
log! str:  "post_trailer: lookup = #{vp.num} #{vp.title}"
  dir = @blog.root/:posts/vp.nslug
log! str:  "  -- dir = #{dir}"
  meta = Dir.chdir(dir) { @blog. }
  nslug = @blog.make_slug(meta)
  aslug = nslug[5..-1]
  proto  = _var("publish.proto")
  server = _var("publish.server")
  path   = _var("publish.path")
  perma = "#{proto}://#{server}/#{path}/#{aslug}.html"
  tags = meta.tags
  taglist = tags.empty? ? "" : "Tags: #{tags}"

  reddit_txt = ""
  if @reddit_enabled
    vdir  = @blog.root/:views/@blog.view
    date  = meta.date
    rid_file = vdir/:posts/nslug/"reddit.id"
    if File.exist?(rid_file) 
 STDERR.puts "    reading #{rid_file}"
      rid = File.read(rid_file).chomp
    else
 STDERR.puts "    creating #{rid_file}"
      title = meta.title
      rid = _reddit_post_url(vdir, date, title, perma)
      dump(rid, rid_file)
    end
    reddit_txt = <<~HTML
      <a name='reddit_comments'>
      <script src='https://redditjs.com/post.js' 
              data-url="#{rid}" data-width=800 ></script>
    HTML
  # damned syntax highlighting </>
  end
# STDERR.print "Pausing... "; getch
  api.out <<~HTML
  #{reddit_txt}
  <hr>
  <table width=100%><tr>
    <td width=10%><a style="text-decoration: none" href="javascript:history.go(-1)">[Back]</a></td>
    <td width=10%><a style="text-decoration: none" href="#{perma}"> [permalink] </a></td>
    <td width=80% align=right><font size=-3>#{taglist}</font></td></tr></table>
  HTML
end

#prefix(num) ⇒ Object

Refactor, move elsewhere?



31
32
33
34
# File 'lib/runeblog_version.rb', line 31

def prefix(num)
  log!(enter: __method__, args: [num], level: 3)
  "#{'%04d' % num.to_i}"
end

#preprocess(cwd: Dir.pwd, src:, dst: nil, strip: false, deps: [], copy: nil, debug: false, force: false, mix: [], call: [], vars: {}) ⇒ Object



23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
# File 'lib/processing.rb', line 23

def preprocess(cwd: Dir.pwd, src:, 
               dst: nil, strip: false,
               deps: [], copy: nil, debug: false, force: false, 
               mix: [], call: [], 
               vars: {})
  src += LEXT unless src.end_with?(LEXT)
  if strip
    dst = File.basename(src).sub(/.lt3$/,"")
  else
    dst += ".html" unless dst.end_with?(".html")
  end
  sp = " "*12

  Dir.chdir(cwd) do
    if debug
      STDERR.puts "#{sp} -- preprocess "
      STDERR.puts "#{sp}      src:  #{src}"
      STDERR.puts "#{sp}      dst:  #{dst}"
      STDERR.puts "#{sp}      in:   #{Dir.pwd}"
      STDERR.puts "#{sp}      from: #{caller[0]}"
      STDERR.puts "#{sp}      copy: #{copy}" if copy
      STDERR.puts "#{sp}      vars: #{vars.inspect}" unless vars == {}
      STDERR.flush
    end
    stale = stale?(src, dst, deps, force)
    STDERR.puts <<~EOF if debug
      STALE = #{stale}
      cwd = #{cwd.inspect}
      src = #{src.inspect}
      dst = #{dst.inspect}
      strip = #{strip.inspect}
      deps = #{deps.inspect}
      copy = #{copy.inspect}
      debug = #{debug.inspect}
      force = #{force.inspect}
      mix = #{mix.inspect}
      call = #{call.inspect}
      vars = #{vars.inspect}
    EOF
    if stale
      live = Livetext.customize(mix: "liveblog", call: call, vars: vars)
      log!(str: "Calling xform_file... src = #{src} pwd = #{Dir.pwd}")
      out = live.xform_file(src)
      File.write(dst, out)
      system!("cp #{dst} #{copy}") if copy
    end
    puts "#{sp} -- ^ Already up to date!" if debug && ! stale
  end
rescue => err
  msg = err.to_s
  msg << err.backtrace.join("\n") if err.respond_to?(:backtrace)
  STDERR.puts msg
  STDERR.flush
  log!(str: msg) 
end

#pubdateObject

Raises:

  • (NoPostCall)


412
413
414
415
416
417
418
419
420
421
422
423
# File 'lib/liveblog.rb', line 412

def pubdate
  log!(enter: __method__)
  raise NoPostCall unless @meta
  api.debug "data = #@_data"
  # Check for discrepancy?
  match = /(\d{4}).(\d{2}).(\d{2})/.match @_data
  junk, y, m, d = match.to_a
  y, m, d = y.to_i, m.to_i, d.to_i
  @meta.date = ::Date.new(y, m, d)
  @meta.pubdate = "%04d-%02d-%02d" % [y, m, d]
  api.optional_blank_line
end

#quit_postObject



53
54
55
# File 'lib/newpost.rb', line 53

def quit_post
  puts __method__
end

#quoteObject



306
307
308
309
310
311
312
# File 'lib/liveblog.rb', line 306

def quote
  log!(enter: __method__)
  _passthru "<blockquote>"
  _passthru api.body.join(" ")
  _passthru "</blockquote>"
  _optional_blank_line
end

#read_pairs(file) ⇒ Object

returns a hash



49
50
51
52
53
54
55
56
57
58
59
# File 'lib/lowlevel.rb', line 49

def read_pairs(file)       # returns a hash
  log!(enter: __method__, args: [file], level: 2)
  lines = _get_data(file)
  hash = {}
  lines.each do |line|
    key, val = line.split(" ", 2)
    val ||= ""
    hash[key] = val
  end
  hash
end

#read_pairs!(file) ⇒ Object

returns an openstruct



61
62
63
64
65
66
67
68
69
70
71
# File 'lib/lowlevel.rb', line 61

def read_pairs!(file)       # returns an openstruct
  log!(enter: __method__, args: [file], level: 2)
  lines = _get_data(file)
  obj = OpenStruct.new
  lines.each do |line|
    key, val = line.split(" ", 2)
    val ||= ""
    obj.send("#{key}=", val)
  end
  obj
end

#recent_postsObject

side-effect



575
576
577
578
579
580
581
582
583
584
# File 'lib/liveblog.rb', line 575

def recent_posts    # side-effect
  log!(enter: __method__)
  api.out <<-HTML
    <div class="col-lg-9 col-md-9 col-sm-9 col-xs-12">
      <iframe id="main" style="width: 70vw; height: 100vh; position: relative;" 
       src='recent.html' width=100% frameborder="0" allowfullscreen>
      </iframe>
    </div>
  HTML
end

#save_postObject



49
50
51
# File 'lib/newpost.rb', line 49

def save_post
  puts __method__
end

#scriptObject



668
669
670
671
672
673
674
675
# File 'lib/liveblog.rb', line 668

def script
  log!(enter: __method__)
  lines = api.body
  url = lines[0]
  integ = lines[1]
  cross = lines[2] || "anonymous"
  api.out %[<script src="#{url}" integrity="#{integ}" crossorigin="#{cross}"></script>]
end

#show_top_menuObject



137
138
139
140
141
# File 'lib/menus.rb', line 137

def show_top_menu
  r, c = STDSCR.rc
  STDSCR.topmenu(items: Menu.top_items)
  STDSCR.go r-1, 0
end


624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
# File 'lib/liveblog.rb', line 624

def sidebar
  log!(enter: __method__)
  api.debug "--- handling sidebar\r"
  if api.args.include? "off"
    api.body { }  # iterate, do nothing
    return 
  end

  api.out %[<div class="col-lg-3 col-md-3 col-sm-3 col-xs-12">]

  standard = %w[pinned pages links news]

  lines = api.body.to_a
  lines.each do |token|
    tag = token.chomp.strip.downcase
    wtag = "../../widgets"/tag
    raise CantFindWidgetDir(wtag) unless Dir.exist?(wtag)
    tcard = "#{tag}-card.html"
    case
      when standard.include?(tag)
        _handle_standard_widget(tag)
      else
        raise "Nonstandard widget?"
    end

    api.include_file wtag/tcard
  end
  api.out %[</div>]
rescue => err
  puts "err = #{err}"
  puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
  sleep 6; RubyText.stop
  exit
end

#stale?(src, dst, deps, force = false) ⇒ Boolean

Returns:

  • (Boolean)


12
13
14
15
16
17
18
19
20
21
# File 'lib/processing.rb', line 12

def stale?(src, dst, deps, force = false)
  meh = File.new("/tmp/dammit-#{src.gsub(/\//, "-")}", "w")
  log!(enter: __method__, args: [src, dst], level: 3)
  raise FileNotFound("#{Dir.pwd}/#{src}") unless File.exist?(src)
  return true if force
  return true unless File.exist?(dst)
  return true if newer?(src, dst)
  deps.each {|dep| return true if newer?(dep, dst) }
  return false
end

#styleObject



318
319
320
321
322
# File 'lib/liveblog.rb', line 318

def style
  log!(enter: __method__)
  fname = api.args[0]
  _passthru %[<link rel="stylesheet" href="???/etc/#{fname}')">]
end

#stylesheetObject



659
660
661
662
663
664
665
666
# File 'lib/liveblog.rb', line 659

def stylesheet
  log!(enter: __method__)
  lines = api.body
  url = lines[0]
  integ = lines[1]
  cross = lines[2] || "anonymous"
  api.out %[<link rel="stylesheet" href="#{url}" integrity="#{integ}" crossorigin="#{cross}"></link>]
end

#system!(os_cmd, show: false) ⇒ Object



17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
# File 'lib/lowlevel.rb', line 17

def system!(os_cmd, show: false)
  log!(enter: __method__, args: [os_cmd], level: 2)
  STDERR.puts os_cmd if show
  rc = system(os_cmd)
  STDERR.puts "  rc = #{rc.inspect}" if show
  return rc if rc
  STDERR.puts "FAILED: #{os_cmd.inspect}"
  STDERR.puts "\ncaller = \n#{caller.join("\n  ")}\n"
  if defined?(RubyText)
    sleep 6
    RubyText.stop
    exit
  end
  return rc
end

#tag_cloudObject



718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
# File 'lib/liveblog.rb', line 718

def tag_cloud
  log!(enter: __method__)
  title = api.data
  title = "Tag Cloud" if title.empty?
  open = <<-HTML
        <div class="card mb-3">
          <div class="card-body">
            <h5 class="card-title">
              <button type="button" class="btn btn-primary" data-toggle="collapse" data-target="#tag-cloud">+</button>
              #{title}
            </h5>
            <div class="collapse" id="tag-cloud">
  HTML
  api.out open
  api.body do |line|
    line.chomp!
    url, classname, cdata = line.split(",", 3)
    main = _main(url)
    api.out %[<a #{main} class="#{classname}">#{cdata}</a>]
  end
  close = %[       </div>\n    </div>\n  </div>]
  api.out close
end

#tagsObject

Raises:

  • (NoPostCall)


425
426
427
428
429
430
431
# File 'lib/liveblog.rb', line 425

def tags
  log!(enter: __method__)
  raise NoPostCall unless @meta
  api.debug "args = #{_args}"
  @meta.tags = api.args.dup || []
  api.optional_blank_line
end

#teaserObject

Raises:

  • (NoPostCall)


472
473
474
475
476
477
478
479
480
481
482
483
484
485
# File 'lib/liveblog.rb', line 472

def teaser
  log!(enter: __method__)
  raise NoPostCall unless @meta
  text = api.body.join("\n")
  @meta.teaser = text
  setvar :teaser, @meta.teaser
  if api.args[0] == "dropcap"   # FIXME doesn't work yet!
    letter, remain = text[0], text[1..-1]
    api.out %[<div class='mydrop'>#{letter}</div>]
    api.out %[<div style="padding-top: 1px">#{remain}] + "\n"
  else
    api.out @meta.teaser + "\n"
  end
end

#timelog(line, file) ⇒ Object



13
14
15
# File 'lib/lowlevel.rb', line 13

def timelog(line, file)
  File.open(file, "a") {|f| f.puts "#{Time.now} #{line}" }
end

#titleObject

Raises:

  • (NoPostCall)


402
403
404
405
406
407
408
409
410
# File 'lib/liveblog.rb', line 402

def title
  log!(enter: __method__)
  raise NoPostCall unless @meta
  title = @_data.chomp
  @meta.title = title
  setvar :title, title
  # FIXME refactor -- just output variables for a template
  api.optional_blank_line
end

#viewsObject

Raises:

  • (NoPostCall)


433
434
435
436
437
438
439
# File 'lib/liveblog.rb', line 433

def views
  log!(enter: __method__)
  raise NoPostCall unless @meta
  api.debug "data = #{_args}"
  @meta.views = api.args.dup
  api.optional_blank_line
end

#vnavbarObject



742
743
744
745
# File 'lib/liveblog.rb', line 742

def vnavbar
  log!(enter: __method__)
  str = _make_navbar(:vert)
end

#write_postObject



461
462
463
464
465
466
467
468
469
470
# File 'lib/liveblog.rb', line 461

def write_post
  log!(enter: __method__)
  raise NoPostCall unless @meta
  @meta.views = @meta.views.join(" ") if @meta.views.is_a? Array
  @meta.tags  = @meta.tags.join(" ") if @meta.tags.is_a? Array
  
rescue => err
  puts "err = #{err}"
  puts err.backtrace.join("\n") if err.respond_to?(:backtrace)
end