summaryrefslogtreecommitdiff
path: root/pkgbuild2mw
blob: 9ee7bff4ed62005727f69c5f36be4306a3977ee9 (plain)
1
2
3
4
5
6
7
8
9
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
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
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
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
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
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
#!/usr/bin/env ruby
# coding: utf-8
load 'pandoc.rb'

class Pass0
	def initialize
		@line = ''
	end

	def getline
		@line = $stdin.readline
	end

	def is_md
		@line.start_with? "#"
	end
	def section_md
		section = ""
		while @line.start_with? "#"
			section += @line.sub(/^# ?/, '')
			getline
		end
		$stdout.puts "\n\n#{Pandoc::load('markdown', section).to('mediawiki')}\n\n"
	end

	def is_hd
		not /(.*[^<])<<\s*([^<]\S+)/.match(@line).nil?
	end
	def section_hd
		m = /(.*[^<])<<\s*([^<]\S+)/.match(@line)
		return if m.nil?
		prefix = m[1]
		eot = m[2]
		getline
		body = ""
		while @line != "#{eot}\n"
			body += @line
			getline
		end
		getline
		body = body.gsub(/\\(.)/, '\1')
		$stdout.puts "\n\n{{hc|#{prefix}|<nowiki>#{body.chomp}</nowiki>}}\n\n"
	end

	def is_hs
		not /(.*[^<])<<<\'(.*)/.match(@line).nil?
	end
	def section_hs
		m = /(.*[^<])<<<\'(.*)/.match(@line)
		return if m.nil?
		prefix = m[1]
		body = m[2] + "\n"
		getline
		while not @line.end_with? "'\n"
			body += @line
			getline
		end
		body += @line.sub(/'$/, '')
		getline
		body = body.gsub("'\\''", "'")
		$stdout.puts "\n\n{{hc|#{prefix}|<nowiki>#{body.chomp}</nowiki>}}\n\n"
	end

	def section_sh
		section = ""
		while true
			if is_md
				$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
				section_md
				section = ""
			elsif is_hd
				$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
				section_hd
				section = ""
			elsif is_hs
				$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
				section_hs
				section = ""
			elsif @line == "postamble\n"
				$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
				return
			else
				if @line.start_with? 'add-unit '
					$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
					$stdout.puts "f* {{ic|/#{@line.sub('add-unit ', '').chomp}}}"
					section = ""
					getline
					next
				end
				m = /^ln -s (.*) (\S*)$/.match(@line)
				if not m.nil?
					$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
					$stdout.puts "f* {{ic|/#{m[2]}}}: {{ic|-> #{m[1]}}}"
					section = ""
					getline
					next
				end
				if @line == "preamble\n" or @line == "postamble" or @line.start_with? 'install -d'
					getline
					next
				end
				if @line.start_with? 'netctl-enable '
					$stdout.puts "\n\n{{bc|<nowiki>#{section.chomp}</nowiki>}}\n\n" unless section.gsub("\n", '') == ""
					unit="netctl@#{`systemd-escape -- #{@line.sub(/^netctl-enable /, '')}`.chomp}.service"
					$stdout.puts "f* {{ic|/etc/systemd/system/#{unit}}}"
					$stdout.puts "f* {{ic|/etc/systemd/system/multi-user.target.wants/#{unit}}}"
					getline
					next
				end
				m = /^depends\+?=\((.*)\)/.match(@line)
				if not m.nil?
					m[1].split(/\s+/).each do |pkg|
						$stdout.puts "p* {{ic|#{pkg}}}"
					end
					getline
					next
				end
				if @line == "depends+=(\n"
					getline
					while @line != ")\n"
						@line.sub(/#.*/, '').split(/\s+/).find_all{|x|not x.empty?}.each do |pkg|
							$stdout.puts "p* {{ic|#{pkg}}}"
						end
						getline
					end
					getline
					next
				end
				m = /^conflicts\+?=\((.*)\)/.match(@line)
				if not m.nil?
					$stdout.puts "p* group:{{ic|base}} except for {{ic|#{m[1]}}}"
					getline
					next
				end
				section += @line
				getline
			end
		end
	end

	def run
		while @line != "preamble\n"
			getline
		end
		getline
		section_sh
	end
end
def pass0
	Pass0.new.run
end

def pass1
	exec('sed', '-r',
	      '-e', 's@^\{\{hc\|add-file (-\S+ )*([^|]*)\|(.*)\}\}$@f* {{ic|/\2}}: {{ic|\3}}@',
	      '-e', 's@^\{\{hc\|add-file (-\S+ )*([^|]*)\|@f* {{ic|/\2}}\n&@',
	      :in=>$stdin, :out=>$stdout)
end

class Pass2
	def initialize
		@pfix = ''
		@ffix = ''
		@body = ''
	end

	def flush
		if @pfix != ''
			$stdout.puts 'Packages installed:'
			$stdout.puts @pfix.split("\n").sort.join("\n")
		end
		if @ffix != ''
			$stdout.puts 'Files affected:'
			$stdout.puts @ffix.split("\n").sort.join("\n")
		end
		$stdout.puts @body
		@pfix = ''
		@ffix = ''
		@body = ''
	end

	def run
		$stdin.each_line do |line|
			if line.start_with? "p*"
				@pfix += line[1,line.length]
			elsif line.start_with? "f*"
				@ffix += line[1,line.length]
			elsif line.start_with? '='
				flush
				$stdout.puts line
			else
				@body += line
			end
		end
		flush
	end
end
def pass2
	Pass2.new.run
end

def pass3
	exec('cat', '-s', :in=>$stdin, :out=>$stdout)
end

# just a utility function for making pipelines
def pipeline(p, i, o)
	ret = []
	if i == :pipe
		r, w = IO.pipe
		i = r
		ret.push(w)
	end
	if o == :pipe
		r, w = IO.pipe
		o = w
		ret.push(r)
	end
	pid = fork {
		$stdin = i
		$stdout = o
		ret.each{|fd| fd.close}

		p.call
	}
	i.close
	o.close
	ret.unshift(pid)
	return ret
end

def main
	# ./pass0 | ./pass1 | ./pass2 | ./pass3
	_, p0 = pipeline(Proc.new{pass0}, $stdin, :pipe  )
	_, p1 = pipeline(Proc.new{pass1}, p0    , :pipe  )
	_, p2 = pipeline(Proc.new{pass2}, p1    , :pipe  )
	_     = pipeline(Proc.new{pass3}, p2    , $stdout)
	Process.waitall
end
main