runeblog 0.3.02
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/README.lt3 +279 -0
- data/README.md +312 -0
- data/bin/blog +200 -0
- data/bin/mkwidget +164 -0
- data/data/EDITOR +1 -0
- data/data/ROOT +1 -0
- data/data/VIEW +1 -0
- data/data/features.txt +18 -0
- data/data/global.lt3 +20 -0
- data/data/universal.lt3 +18 -0
- data/empty_view/assets/austin-pano.jpg +0 -0
- data/empty_view/assets/sky2.jpg +0 -0
- data/empty_view/config/exper/2svg.lt3 +38 -0
- data/empty_view/config/exper/gen_svg.rb +60 -0
- data/empty_view/config/exper/meta.html +10 -0
- data/empty_view/config/exper/s2.html +25 -0
- data/empty_view/config/exper/varmint.rb +50 -0
- data/empty_view/config/facebook/credentials.txt +7 -0
- data/empty_view/config/facebook/facebook.rb +42 -0
- data/empty_view/config/facebook/fb.html +10 -0
- data/empty_view/config/facebook/fb.js.lt3 +15 -0
- data/empty_view/config/reddit/credentials.txt +6 -0
- data/empty_view/config/reddit/notes.txt +4 -0
- data/empty_view/config/reddit/reddit_post_url.py +34 -0
- data/empty_view/config/reddit/redpost.rb +43 -0
- data/empty_view/config/reddit/the-graffiti-wall.html +91 -0
- data/empty_view/config/twitter/credentials.txt +3 -0
- data/empty_view/config/twitter/tw.html +12 -0
- data/empty_view/config/twitter/tw.js +5 -0
- data/empty_view/config/twitter/twitter.rb +35 -0
- data/empty_view/posts/GIT_IS_DUMB +1 -0
- data/empty_view/remote/assets/GIT_IS_DUMB +1 -0
- data/empty_view/remote/banner/navbar/GIT_IS_DUMB +0 -0
- data/empty_view/remote/etc/GIT_IS_DUMB +1 -0
- data/empty_view/remote/permalink/GIT_IS_DUMB +1 -0
- data/empty_view/remote/widgets/ad/GIT_IS_DUMB +2 -0
- data/empty_view/remote/widgets/links/GIT_IS_DUMB +2 -0
- data/empty_view/remote/widgets/news/GIT_IS_DUMB +2 -0
- data/empty_view/remote/widgets/pages/GIT_IS_DUMB +2 -0
- data/empty_view/remote/widgets/pinned/GIT_IS_DUMB +2 -0
- data/empty_view/settings/features.txt +18 -0
- data/empty_view/settings/publish.txt +5 -0
- data/empty_view/settings/recent.txt +6 -0
- data/empty_view/settings/view.txt +4 -0
- data/empty_view/themes/standard/README +59 -0
- data/empty_view/themes/standard/banner/banner.lt3 +5 -0
- data/empty_view/themes/standard/banner/navbar/about.lt3 +18 -0
- data/empty_view/themes/standard/banner/navbar/contact.lt3 +18 -0
- data/empty_view/themes/standard/banner/navbar/faq.lt3 +1 -0
- data/empty_view/themes/standard/banner/navbar/list.data +3 -0
- data/empty_view/themes/standard/banner/top.lt3 +20 -0
- data/empty_view/themes/standard/blog/generate.lt3 +21 -0
- data/empty_view/themes/standard/blog/head.lt3 +16 -0
- data/empty_view/themes/standard/blog/index.lt3 +17 -0
- data/empty_view/themes/standard/blog/post_entry.lt3 +21 -0
- data/empty_view/themes/standard/etc/blog.css.lt3 +62 -0
- data/empty_view/themes/standard/etc/externals.lt3 +24 -0
- data/empty_view/themes/standard/etc/favicon.ico +0 -0
- data/empty_view/themes/standard/etc/misc.js +20 -0
- data/empty_view/themes/standard/post/generate.lt3 +38 -0
- data/empty_view/themes/standard/post/head.lt3 +7 -0
- data/empty_view/themes/standard/post/index.lt3 +24 -0
- data/empty_view/themes/standard/post/permalink.lt3 +32 -0
- data/empty_view/themes/standard/widgets/README +4 -0
- data/empty_view/themes/standard/widgets/ad/ad.lt3 +22 -0
- data/empty_view/themes/standard/widgets/ad/ad1.png +0 -0
- data/empty_view/themes/standard/widgets/ad/ad2.png +0 -0
- data/empty_view/themes/standard/widgets/ad/ad3.png +0 -0
- data/empty_view/themes/standard/widgets/ad/ad4.png +0 -0
- data/empty_view/themes/standard/widgets/bydates/README +2 -0
- data/empty_view/themes/standard/widgets/bydates/bydates.rb +18 -0
- data/empty_view/themes/standard/widgets/bydates/card.css +1 -0
- data/empty_view/themes/standard/widgets/bydates/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/bydates/main.css +2 -0
- data/empty_view/themes/standard/widgets/links/README +2 -0
- data/empty_view/themes/standard/widgets/links/card.css +1 -0
- data/empty_view/themes/standard/widgets/links/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/links/links.rb +90 -0
- data/empty_view/themes/standard/widgets/links/list.data +3 -0
- data/empty_view/themes/standard/widgets/links/main.css +2 -0
- data/empty_view/themes/standard/widgets/news/README +2 -0
- data/empty_view/themes/standard/widgets/news/card.css +1 -0
- data/empty_view/themes/standard/widgets/news/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/news/list.data +4 -0
- data/empty_view/themes/standard/widgets/news/main.css +2 -0
- data/empty_view/themes/standard/widgets/news/news.rb +88 -0
- data/empty_view/themes/standard/widgets/pages/README +2 -0
- data/empty_view/themes/standard/widgets/pages/card.css +1 -0
- data/empty_view/themes/standard/widgets/pages/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/pages/disclaim.lt3 +10 -0
- data/empty_view/themes/standard/widgets/pages/faq.lt3 +40 -0
- data/empty_view/themes/standard/widgets/pages/like-dislike.lt3 +11 -0
- data/empty_view/themes/standard/widgets/pages/list.data +4 -0
- data/empty_view/themes/standard/widgets/pages/local.rb +0 -0
- data/empty_view/themes/standard/widgets/pages/main.css +2 -0
- data/empty_view/themes/standard/widgets/pages/other-stuff.lt3 +10 -0
- data/empty_view/themes/standard/widgets/pages/pages.rb +95 -0
- data/empty_view/themes/standard/widgets/pinned/README +2 -0
- data/empty_view/themes/standard/widgets/pinned/card.css +1 -0
- data/empty_view/themes/standard/widgets/pinned/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/pinned/main.css +2 -0
- data/empty_view/themes/standard/widgets/pinned/pinned.rb +99 -0
- data/empty_view/themes/standard/widgets/search/README +2 -0
- data/empty_view/themes/standard/widgets/search/card.css +1 -0
- data/empty_view/themes/standard/widgets/search/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/search/main.css +2 -0
- data/empty_view/themes/standard/widgets/search/search.rb +18 -0
- data/empty_view/themes/standard/widgets/sitemap/README +2 -0
- data/empty_view/themes/standard/widgets/sitemap/card.css +1 -0
- data/empty_view/themes/standard/widgets/sitemap/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/sitemap/main.css +2 -0
- data/empty_view/themes/standard/widgets/sitemap/sitemap.rb +18 -0
- data/empty_view/themes/standard/widgets/tag-cloud/OLD-example.lt3 +12 -0
- data/empty_view/themes/standard/widgets/tag-cloud/README +2 -0
- data/empty_view/themes/standard/widgets/tag-cloud/card.css +1 -0
- data/empty_view/themes/standard/widgets/tag-cloud/custom.rb +1 -0
- data/empty_view/themes/standard/widgets/tag-cloud/main.css +2 -0
- data/empty_view/themes/standard/widgets/tag-cloud/tag-cloud.lt3 +3 -0
- data/empty_view/themes/standard/widgets/tag-cloud/tag-cloud.rb +18 -0
- data/lib/Javascript.stuff +69 -0
- data/lib/helpers-blog.rb +155 -0
- data/lib/helpers-repl.rb +201 -0
- data/lib/liveblog.rb +825 -0
- data/lib/logging.rb +44 -0
- data/lib/lowlevel.rb +73 -0
- data/lib/pathmagic.rb +14 -0
- data/lib/post.rb +211 -0
- data/lib/processing.rb +60 -0
- data/lib/publish.rb +73 -0
- data/lib/repl.rb +597 -0
- data/lib/runeblog.rb +773 -0
- data/lib/runeblog_version.rb +50 -0
- data/lib/view.rb +69 -0
- data/runeblog.gemspec +42 -0
- data/test/austin.rb +158 -0
- data/test/fakeimage.jpg +0 -0
- data/test/general_test.rb +304 -0
- data/test/make_blog.rb +196 -0
- data/test/test +3 -0
- metadata +242 -0
data/lib/logging.rb
ADDED
@@ -0,0 +1,44 @@
|
|
1
|
+
unless self.respond_to?("log!")
|
2
|
+
$logging = true
|
3
|
+
$log = File.new("/tmp/runeblog.log","w")
|
4
|
+
|
5
|
+
def outlog(str = "", stderr: false)
|
6
|
+
$log.puts str
|
7
|
+
STDERR.puts str if stderr
|
8
|
+
end
|
9
|
+
|
10
|
+
def log!(str: "", enter: nil, args: [], pwd: false, dir: false, level: 0, stderr: false)
|
11
|
+
return unless $logging
|
12
|
+
@err_level ||= ENV['RUNEBLOG_ERROR_LEVEL']
|
13
|
+
@err_level ||= 0
|
14
|
+
return if level < @err_level
|
15
|
+
|
16
|
+
time = Time.now.strftime("%H:%M:%S")
|
17
|
+
|
18
|
+
meth = ""
|
19
|
+
meth = "#{enter}" if enter
|
20
|
+
|
21
|
+
para = "(#{args.inspect[1..-2]})"
|
22
|
+
|
23
|
+
source = caller[0].sub(/.*\//, " in ").sub(/:/, " line ").sub(/:.*/, "")
|
24
|
+
source = "in #{source} (probably liveblog.rb)" if source.include? "(eval)"
|
25
|
+
|
26
|
+
str = " ... #{str}" unless str.empty?
|
27
|
+
indent = " "*12
|
28
|
+
|
29
|
+
outlog "#{time} #{meth}#{para}"
|
30
|
+
outlog "#{indent} #{str} " unless str.empty?
|
31
|
+
outlog "#{indent} #{source}"
|
32
|
+
outlog "#{indent} pwd = #{Dir.pwd} " if pwd
|
33
|
+
if dir
|
34
|
+
files = (Dir.entries('.') - %w[. ..]).join(" ")
|
35
|
+
outlog "#{indent} dir/* = #{files}"
|
36
|
+
end
|
37
|
+
# outlog "#{indent} livetext params = #{livedata.inpect} " unless livedata.nil?
|
38
|
+
outlog
|
39
|
+
$log.close
|
40
|
+
$log = File.new("/tmp/runeblog.log","a")
|
41
|
+
end
|
42
|
+
|
43
|
+
end
|
44
|
+
|
data/lib/lowlevel.rb
ADDED
@@ -0,0 +1,73 @@
|
|
1
|
+
|
2
|
+
def dump(obj, name)
|
3
|
+
File.write(name, obj)
|
4
|
+
end
|
5
|
+
|
6
|
+
def system!(str, show: false)
|
7
|
+
log!(enter: __method__, args: [str], level: 2)
|
8
|
+
STDERR.puts str if show
|
9
|
+
rc = system(str)
|
10
|
+
return rc if rc
|
11
|
+
STDERR.puts "FAILED: #{str.inspect}"
|
12
|
+
STDERR.puts "\ncaller = \n#{caller.join("\n ")}\n"
|
13
|
+
if defined?(RubyText)
|
14
|
+
sleep 6
|
15
|
+
RubyText.stop
|
16
|
+
exit
|
17
|
+
end
|
18
|
+
return rc
|
19
|
+
end
|
20
|
+
|
21
|
+
def _get_data?(file) # File need not exist
|
22
|
+
if File.exist?(file)
|
23
|
+
_get_data(file)
|
24
|
+
else
|
25
|
+
[]
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def _get_data(file)
|
30
|
+
lines = File.readlines(file)
|
31
|
+
lines.reject! {|line| line[0] == "-" } # allow rejection of lines
|
32
|
+
lines = lines.map do |line|
|
33
|
+
line.sub(/ *# .*$/, "") # allow trailing comments
|
34
|
+
end
|
35
|
+
lines
|
36
|
+
end
|
37
|
+
|
38
|
+
def copy(src, dst)
|
39
|
+
log!(enter: __method__, args: [src, dst], level: 2)
|
40
|
+
cmd = "cp #{src} #{dst} 2>/dev/null"
|
41
|
+
system!(cmd)
|
42
|
+
end
|
43
|
+
|
44
|
+
def copy!(src, dst)
|
45
|
+
log!(enter: __method__, args: [src, dst], level: 2)
|
46
|
+
cmd = "cp -r #{src} #{dst} 2>/dev/null"
|
47
|
+
system!(cmd)
|
48
|
+
end
|
49
|
+
|
50
|
+
def create_dirs(*dirs)
|
51
|
+
log!(enter: __method__, args: [*dirs], level: 3)
|
52
|
+
dirs.each do |dir|
|
53
|
+
dir = dir.to_s # symbols allowed
|
54
|
+
next if Dir.exist?(dir)
|
55
|
+
cmd = "mkdir -p #{dir} >/dev/null"
|
56
|
+
result = system!(cmd)
|
57
|
+
raise CantCreateDir(dir) unless result
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
def interpolate(str, bind)
|
62
|
+
log!(enter: __method__, args: [str, bind], level: 3)
|
63
|
+
wrap = "<<-EOS\n#{str}\nEOS"
|
64
|
+
eval wrap, bind
|
65
|
+
end
|
66
|
+
|
67
|
+
def error(err)
|
68
|
+
log!(str: err, enter: __method__, args: [err], level: 2)
|
69
|
+
str = "\n Error: #{err}"
|
70
|
+
puts str
|
71
|
+
puts err.backtrace.join("\n")
|
72
|
+
end
|
73
|
+
|
data/lib/pathmagic.rb
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
module PathSep
|
2
|
+
def /(right)
|
3
|
+
s1 = self.to_s.dup
|
4
|
+
s2 = right.to_s.dup
|
5
|
+
s1 << "/" unless s1.end_with?("/") || s2.start_with?("/")
|
6
|
+
path = s1 + s2
|
7
|
+
path.gsub!("//", "/")
|
8
|
+
path
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
String.include(PathSep)
|
13
|
+
Symbol.include(PathSep)
|
14
|
+
|
data/lib/post.rb
ADDED
@@ -0,0 +1,211 @@
|
|
1
|
+
require 'runeblog'
|
2
|
+
require 'pathmagic'
|
3
|
+
|
4
|
+
class RuneBlog::Post
|
5
|
+
|
6
|
+
attr_reader :num, :title, :date, :views, :num, :slug
|
7
|
+
attr_accessor :meta, :blog, :draft
|
8
|
+
|
9
|
+
include RuneBlog::Helpers
|
10
|
+
|
11
|
+
|
12
|
+
def self.load(post)
|
13
|
+
log!(enter: __method__, args: [post], level: 3)
|
14
|
+
raise "Doesn't work right now"
|
15
|
+
raise NoBlogAccessor if RuneBlog.blog.nil?
|
16
|
+
# "post" is a slug
|
17
|
+
pdir = RuneBlog.blog.root/:drafts/post
|
18
|
+
meta = nil
|
19
|
+
Dir.chdir(pdir) do
|
20
|
+
meta = read_config("metadata.txt")
|
21
|
+
meta.date = Date.parse(meta.date)
|
22
|
+
meta.views = meta.views.split
|
23
|
+
meta.tags = meta.tags.split
|
24
|
+
meta.teaser = File.read("teaser.txt")
|
25
|
+
# meta.body = File.read("body.txt")
|
26
|
+
end
|
27
|
+
meta
|
28
|
+
end
|
29
|
+
|
30
|
+
def write_metadata(meta) # FIXME ???
|
31
|
+
log!(enter: __method__, args: [meta], level: 3)
|
32
|
+
debug "=== write_metadata:"
|
33
|
+
debug "-----\n#{meta.inspect}\n-----"
|
34
|
+
fname2 = "metadata.txt"
|
35
|
+
hash = meta.to_h
|
36
|
+
|
37
|
+
File.write("teaser.txt", hash[:teaser])
|
38
|
+
hash.delete(:teaser)
|
39
|
+
hash.delete(:body)
|
40
|
+
|
41
|
+
hash[:views] = hash[:views].join(" ")
|
42
|
+
hash[:tags] = hash[:tags].join(" ")
|
43
|
+
|
44
|
+
fields = [:num, :title, :date, :pubdate, :views, :tags]
|
45
|
+
|
46
|
+
f2 = File.new(fname2, "w")
|
47
|
+
fields.each {|fld| f2.puts "#{fld}: #{hash[fld]}" }
|
48
|
+
f2.close
|
49
|
+
end
|
50
|
+
|
51
|
+
def initialize
|
52
|
+
log!(enter: __method__, level: 3)
|
53
|
+
@blog = RuneBlog.blog || raise(NoBlogAccessor)
|
54
|
+
@meta = OpenStruct.new
|
55
|
+
end
|
56
|
+
|
57
|
+
def self.create(title:, teaser:, body:, pubdate: Time.now.strftime("%Y-%m-%d"),
|
58
|
+
views:[], file: nil)
|
59
|
+
log!(enter: __method__, args: [title, teaser, body, pubdate, views], stderr: true)
|
60
|
+
post = self.new
|
61
|
+
# NOTE: This is the ONLY place next_sequence is called!
|
62
|
+
num = post.meta.num = post.blog.next_sequence
|
63
|
+
|
64
|
+
# new_metadata
|
65
|
+
post.meta.title, post.meta.teaser, post.meta.body, post.meta.pubdate =
|
66
|
+
title, teaser, body, pubdate
|
67
|
+
post.meta.views = [post.blog.view.to_s] + views
|
68
|
+
post.meta.tags = []
|
69
|
+
post.blog.make_slug(post.meta) # adds to meta
|
70
|
+
|
71
|
+
# create_draft
|
72
|
+
viewhome = post.blog.view.publisher.url
|
73
|
+
meta = post.meta
|
74
|
+
if file.nil?
|
75
|
+
text = RuneBlog.post_template(num: meta.num, title: meta.title, date: meta.pubdate,
|
76
|
+
view: meta.view, teaser: meta.teaser, body: meta.body,
|
77
|
+
views: meta.views, tags: meta.tags, home: viewhome)
|
78
|
+
srcdir = post.blog.root/:drafts + "/"
|
79
|
+
vpdir = post.blog.root/:drafts + "/"
|
80
|
+
fname = meta.slug + ".lt3"
|
81
|
+
post.draft = srcdir + fname
|
82
|
+
dump(text, post.draft)
|
83
|
+
else
|
84
|
+
dump(File.read(file), post.draft)
|
85
|
+
end
|
86
|
+
return post
|
87
|
+
end
|
88
|
+
|
89
|
+
def edit
|
90
|
+
log!(enter: __method__)
|
91
|
+
result = system!("vi #@draft +8") # TODO improve this
|
92
|
+
raise EditorProblem(draft) unless result
|
93
|
+
nil
|
94
|
+
rescue => err
|
95
|
+
error(err)
|
96
|
+
end
|
97
|
+
|
98
|
+
def build
|
99
|
+
log!(enter: __method__)
|
100
|
+
post = self
|
101
|
+
views = post.meta.views
|
102
|
+
text = File.read(@draft)
|
103
|
+
@blog.generate_post(@draft)
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
class RuneBlog::ViewPost
|
108
|
+
attr_accessor :nslug, :aslug, :num, :view, :blog
|
109
|
+
attr_accessor :path, :title, :date, :teaser_text
|
110
|
+
|
111
|
+
def self.make(blog:, view:, nslug:)
|
112
|
+
raise "No numeric prefix on #{nslug}" unless nslug =~ /^\d{4}-/
|
113
|
+
raise "Not expecting an extension" if nslug.end_with?(".lt3") || nslug.end_with?(".html")
|
114
|
+
view = view.to_s
|
115
|
+
view.define_singleton_method :path do |subdir = ""|
|
116
|
+
str = blog.root/:views/view
|
117
|
+
str << "/#{subdir}" unless subdir.empty?
|
118
|
+
str
|
119
|
+
end
|
120
|
+
view.define_singleton_method :standard do |subdir = ""|
|
121
|
+
str = blog.root/:views/view/:themes/:standard
|
122
|
+
str << "/#{subdir}" unless subdir.empty?
|
123
|
+
str
|
124
|
+
end
|
125
|
+
view.define_singleton_method :postdir do |file = ""|
|
126
|
+
file = file.to_s
|
127
|
+
str = blog.root/:views/view/:posts/nslug
|
128
|
+
str = str/file unless file.empty?
|
129
|
+
str
|
130
|
+
end
|
131
|
+
view.define_singleton_method :remote do |dir: "", file: ""|
|
132
|
+
subdir = subdir.to_s
|
133
|
+
file = file.to_s
|
134
|
+
str = blog.root/:views/view/:remote
|
135
|
+
str = str/subdir unless subdir.empty?
|
136
|
+
str = str/file unless file.empty?
|
137
|
+
str
|
138
|
+
end
|
139
|
+
obj = RuneBlog::ViewPost.new(view, nslug)
|
140
|
+
obj.blog = blog
|
141
|
+
obj.view = view
|
142
|
+
obj.nslug = nslug
|
143
|
+
obj.aslug = nslug[5..-1]
|
144
|
+
obj.num = nslug[0..3]
|
145
|
+
obj
|
146
|
+
end
|
147
|
+
|
148
|
+
def repo(subdir = "")
|
149
|
+
subdir = subdir.to_s
|
150
|
+
unless subdir.empty?
|
151
|
+
raise "Expected 'posts' or 'drafts'" unless %w[posts drafts].include?(subdir)
|
152
|
+
end
|
153
|
+
str = blog.root
|
154
|
+
str = str/subdir unless subdir.empty?
|
155
|
+
str
|
156
|
+
end
|
157
|
+
|
158
|
+
alias root repo
|
159
|
+
|
160
|
+
def slug(num = true, ext = "")
|
161
|
+
ext = ext.to_s
|
162
|
+
str = ""
|
163
|
+
str << @num << "-" if num
|
164
|
+
str << @aslug
|
165
|
+
str << ext
|
166
|
+
str
|
167
|
+
end
|
168
|
+
|
169
|
+
=begin
|
170
|
+
aslug this-is-a-post
|
171
|
+
aslug_live this-is-a-post.lt3
|
172
|
+
aslug_html this-is-a-post.lt3
|
173
|
+
nslug 0001-this-is-a-post
|
174
|
+
|
175
|
+
slug(:num, ext = "")
|
176
|
+
=end
|
177
|
+
|
178
|
+
def initialize(view, postdir)
|
179
|
+
log!(enter: __method__, args: [view, postdir], level: 3)
|
180
|
+
# Assumes already parsed/processed
|
181
|
+
@blog = RuneBlog.blog || raise(NoBlogAccessor)
|
182
|
+
@path = postdir.dup
|
183
|
+
@nslug = @path.split("/").last
|
184
|
+
@aslug = @nslug[5..-1]
|
185
|
+
fname = "#{postdir}/teaser.txt" # ???
|
186
|
+
@teaser_text = File.read(fname).chomp
|
187
|
+
# FIXME dumb hacks...
|
188
|
+
mdfile = postdir/"metadata.txt"
|
189
|
+
lines = File.readlines(mdfile)
|
190
|
+
@title = lines.grep(/title:/).first[7..-1].chomp
|
191
|
+
@date = lines.grep(/pubdate:/).first[9..-1].chomp
|
192
|
+
# print "-- date = #{@date.inspect} "; gets
|
193
|
+
rescue => err
|
194
|
+
STDERR.puts "--- #{err}\n #{err.backtrace.join("\n ")}"
|
195
|
+
end
|
196
|
+
|
197
|
+
def get_dirs
|
198
|
+
log!(enter: __method__, args: [view, postdir], level: 3)
|
199
|
+
fname = File.basename(draft)
|
200
|
+
noext = fname.sub(/.lt3$/, "")
|
201
|
+
vdir = @root/:views/view
|
202
|
+
dir = vdir/:posts/noext + "/"
|
203
|
+
Dir.mkdir(dir) unless Dir.exist?(dir)
|
204
|
+
system!("cp #{draft} #{dir}")
|
205
|
+
viewdir, slugdir, aslug = vdir, dir, noext[5..-1]
|
206
|
+
theme = viewdir/:themes/:standard
|
207
|
+
[noext, viewdir, slugdir, aslug, theme]
|
208
|
+
end
|
209
|
+
|
210
|
+
end
|
211
|
+
|
data/lib/processing.rb
ADDED
@@ -0,0 +1,60 @@
|
|
1
|
+
if ! defined?(LIVE)
|
2
|
+
|
3
|
+
require 'livetext'
|
4
|
+
|
5
|
+
LIVE = Livetext.new
|
6
|
+
LEXT = ".lt3"
|
7
|
+
|
8
|
+
def newer?(f1, f2)
|
9
|
+
File.mtime(f1) > File.mtime(f2)
|
10
|
+
end
|
11
|
+
|
12
|
+
def stale?(src, dst, deps, force = false)
|
13
|
+
meh = File.new("/tmp/dammit-#{src.gsub(/\//, "-")}", "w")
|
14
|
+
log!(enter: __method__, args: [src, dst], level: 3)
|
15
|
+
raise "Source #{src} not found in #{Dir.pwd}" unless File.exist?(src)
|
16
|
+
return true if force
|
17
|
+
return true unless File.exist?(dst)
|
18
|
+
return true if newer?(src, dst)
|
19
|
+
deps.each {|dep| return true if newer?(dep, dst) }
|
20
|
+
return false
|
21
|
+
end
|
22
|
+
|
23
|
+
def preprocess(cwd: Dir.pwd, src:,
|
24
|
+
dst: nil, strip: false,
|
25
|
+
deps: [], copy: nil, debug: false, force: false,
|
26
|
+
mix: [], call: [], vars: {})
|
27
|
+
src += LEXT unless src.end_with?(LEXT)
|
28
|
+
if strip
|
29
|
+
dst = File.basename(src).sub(/.lt3$/,"")
|
30
|
+
else
|
31
|
+
dst += ".html" unless dst.end_with?(".html")
|
32
|
+
end
|
33
|
+
sp = " "*12
|
34
|
+
Dir.chdir(cwd) do
|
35
|
+
if debug
|
36
|
+
STDERR.puts "#{sp} -- preprocess "
|
37
|
+
STDERR.puts "#{sp} src: #{src}"
|
38
|
+
STDERR.puts "#{sp} dst: #{dst}"
|
39
|
+
STDERR.puts "#{sp} in: #{Dir.pwd}"
|
40
|
+
STDERR.puts "#{sp} from: #{caller[0]}"
|
41
|
+
STDERR.puts "#{sp} copy: #{copy}" if copy
|
42
|
+
end
|
43
|
+
stale = stale?(src, dst, deps, force)
|
44
|
+
if stale
|
45
|
+
live = Livetext.customize(mix: "liveblog", call: call, vars: vars)
|
46
|
+
out = live.xform_file(src)
|
47
|
+
File.write(dst, out)
|
48
|
+
system!("cp #{dst} #{copy}") if copy
|
49
|
+
end
|
50
|
+
puts "#{sp} -- ^ Already up to date!" if debug && ! stale
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def get_live_vars(src)
|
55
|
+
live = Livetext.customize(call: [".nopara"])
|
56
|
+
live.xform_file(src)
|
57
|
+
live
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
data/lib/publish.rb
ADDED
@@ -0,0 +1,73 @@
|
|
1
|
+
if ! defined?(Already_publish)
|
2
|
+
|
3
|
+
Already_publish = nil
|
4
|
+
|
5
|
+
require 'pathmagic'
|
6
|
+
require 'processing'
|
7
|
+
|
8
|
+
class RuneBlog::Publishing
|
9
|
+
attr_reader :user, :server, :docroot, :path
|
10
|
+
|
11
|
+
BadRemoteLogin = Exception.new("Can't login remotely")
|
12
|
+
BadRemotePerms = Exception.new("Bad remote permissions")
|
13
|
+
|
14
|
+
def initialize(view)
|
15
|
+
log!(enter: __method__, args: [view.to_s])
|
16
|
+
@blog = RuneBlog.blog
|
17
|
+
dir = @blog.root/:views/view/"themes/standard/"
|
18
|
+
gfile = dir/"global.lt3"
|
19
|
+
return unless File.exist?(gfile) # FIXME Hackish as hell
|
20
|
+
|
21
|
+
live = get_live_vars(gfile)
|
22
|
+
@user = live.vars["publish.user"]
|
23
|
+
@server = live.vars["publish.server"]
|
24
|
+
@docroot = live.vars["publish.docroot"]
|
25
|
+
@path = live.vars["publish.path"]
|
26
|
+
@proto = live.vars["publish.proto"]
|
27
|
+
end
|
28
|
+
|
29
|
+
def to_h
|
30
|
+
log!(enter: __method__, level: 3)
|
31
|
+
{user: @user, server: @server, docroot: @docroot,
|
32
|
+
path: @path, proto: @proto}
|
33
|
+
end
|
34
|
+
|
35
|
+
def url
|
36
|
+
log!(enter: __method__, level: 3)
|
37
|
+
vname = @blog.view.name # .gsub(/_/, "\\_")
|
38
|
+
url = "#@proto://#@server/#@path" # /#{vname}"
|
39
|
+
end
|
40
|
+
|
41
|
+
def publish
|
42
|
+
log!(enter: __method__, level: 1)
|
43
|
+
dir = @docroot/@path
|
44
|
+
view_name = @blog.view.name
|
45
|
+
viewpath = dir # /view_name
|
46
|
+
# FIXME rsync doesn't work
|
47
|
+
cmd = "rsync -r -z #{@blog.root}/views/#{@blog.view}/remote/ #@user@#@server:#{viewpath}/"
|
48
|
+
system!(cmd)
|
49
|
+
dump("#{@blog.view} at #{Time.now}", "#{@blog.view.dir}/last_published")
|
50
|
+
true
|
51
|
+
end
|
52
|
+
|
53
|
+
def remote_login?
|
54
|
+
log!(enter: __method__)
|
55
|
+
cmd = "ssh -o BatchMode=yes #@user@#@server -x date >/dev/null 2>&1"
|
56
|
+
result = system(cmd)
|
57
|
+
return nil unless result
|
58
|
+
true
|
59
|
+
end
|
60
|
+
|
61
|
+
def remote_permissions?
|
62
|
+
log!(enter: __method__)
|
63
|
+
dir = @docroot/@path
|
64
|
+
temp = @path/"__only_testing"
|
65
|
+
try1 = system("ssh -o BatchMode=yes -o ConnectTimeout=1 #@user@#@server -x mkdir -p #{temp} >/dev/null 2>&1")
|
66
|
+
return nil unless try1
|
67
|
+
try2 = system("ssh -o BatchMode=yes -o ConnectTimeout=1 #@user@#@server -x rmdir #{temp} >/dev/null 2>&1")
|
68
|
+
return nil unless try2
|
69
|
+
true
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
end
|