-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy patht2tmake.rb
executable file
·464 lines (416 loc) · 13.6 KB
/
t2tmake.rb
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
241
242
243
244
245
246
247
248
249
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
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
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
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
#!/usr/bin/env ruby
require 'optparse'
require 'fileutils'
=begin
:title: Documentação do t2t-make
= t2tmake.rb (0.8beta)
Programa para o processamento automatico de arquivos utilizando
o txt2tags <t2t> (http://txt2tags.org)
== download e instalação
Existem duas maneiras de baixar este programa:
- Na área de arquivos da lista[http://groups.yahoo.com/group/txt2tags-br].
dos usuários do txt2tags (em português)
- Na página[http://txt2tags-win.sourceforge.net/t2tmake.zip] em português do txt2tags.
===requisitos
- txt2tags (é claro, sem ele este programa não existiria);
- ruby 1.6.8+ (é lógico, senão este programa não roda);
- python 1.5+ (sim, sim, para o txt2tags rodar);
===instalação: (t2t)
- txt2tags: verifique o site http://txt2tags.org;
- python: verifique o site www.python.org;
===instalação (ruby)
- Windows:
Baixe de http://rubyinstaller.sourceforge.net e execute o
programa de instalação.
- Linux:
A maioria das grandes distribuições já possuem o pacote em
algum CD. Siga os procedimentos normais de instalação. Caso
não exista para a sua, baixe os fontes de
http://www.ruby-lang.org/en/ e siga os procedimentos.
- Mac OSX:
As versões atuais já trazem o Ruby. Caso contrário seria
necessário baixar os fontes de http://www.ruby-lang.org/en/
e compilar.
- Cygwin:
Rode o programa de setup, e instale a versão compilada do
Ruby (1.6.8).
- Outros:
Não tenho idéia. Só vendo.
===instalação (programa)
- apenas copie o programa para o local de sua preferência (em
um local onde ele possa ser executado sem especificar o
caminho é uma boa idéia)
==características
- processa apenas os arquivos necessários (atualizados ou inexistentes);
- permite o processamento recursivo (subdiretórios);
- gera log dos arquivos para facilitar a atualização de sites;
- roda em Windows, Linux, Cygwin, (etc?)
- opção para adequação de indexes localizados para o Apache,
index-ptbr.t2t => index.html.ptbr
- aceita opções a partir de um arquivo de configuração (+veja observações abaixo+)
- permite listar os rótulos existentes no arquivo de configuração
===Obs:
==== --batch filename rótulo
- deve ser a última opção da linha de comando
- as opções anteriores mantidas são: --clean --all
- o arquivo contendo as opções é um arquivo texto no seguinte formato:
- os rótulos devem estar entre chaves
- deixar uma linha em branco para separar os rótulos
- caminhos contendo espaçoes deverão estar entre aspas "caminho"
[rotulo]
--opção
...
--opção
ex.:
[txt2tags-win]
--L10N
--type html
--sdir "C:/Arquivos de programas/Apache Group/Apache/htdocs/txt2tags-win"
--ddir "C:/Arquivos de programas/Apache Group/Apache/htdocs/txt2tags-win"
-r
==por fazer:
- inclusão de opções de pesquisa (--todo e --find text|ER)
- inclusão de opções de alteração (--subs texto:texto)
- aceitar outras opções para enviar ao t2t
- ??
= copyright
(C) 2003 por Guaracy Monteiro (http://ruby-ptbr.rubyforge.org/)
= licenças
GPL + Ruby (ou seja, faça o uso que desejar)
= historico
[A]lteração; Correção de [B]ugs; [N]ovo
25/08/2003
- lançamento (testes iniciais no Mandrake 9.1 e Windows 2000 utilizando
ruby 1.8 e no Cygwin utilizando ruby 1.6.8)
30/08/2003
- [A]alterações nos comentários do programa para a geração automática
da documentação pelo rdoc;
- [A]alterações em nomes de variáveis e métodos do programa
bem como de opções aceitas pelo mesmos e respectivas rotinas;
- [B]passagem de diretório com espaços para o txt2tags;
- [N]opção L10N para arquivos de indices do Apache. Executada
apenas para --type html
index-en.t2t, index-ptbr.t2t => index.html.en, index.html.ptbr;
- [N]opção --batch filename label. Abre um arquivo de configuração
(default => t2t-make.conf), procura pelo rótulo especificado e
passa para a linha de comandos as opções encontradas no arquivo
(encerra na primeira linha em branco);
- [N]opção -L. Utilizada em conjunto com a opção --batch e serve
para apenas listar os rótulos encontrados no arquivo sem a
execução do mesmo;
- [A]separação da rotina para interpretar a linha de comandos
para facilitar a execução de arquivos de lotes;
- [N]opção --ext extensão para gerar arquivo com extensão
diferente da padrão;
- [N]opção --all para forçar a atualização de todos os arquivos
09/07/2004
- [A]correções diversas para atualização
10/07/2004
- [A]utilização de optparse para verificação das opções
- [A]exclusão do parâmetro -L
- [N]parâmetro -b/--batch lista rótulo em caso de omissão ou erro
- [A]alteração dos métodos para tratamento de arquivos batch
- [N]lançamento da versão 1.0rc
- [A]exclusão do método usage (incorporado na verificação dos parâmetros)
- [A]alterações em diversas partes do programa por conta da 'optparse'
- [N]é salvo a data e os dados são adicionados no logfile
=end
# versão do programa
$VERSAO = "1.0rc"
#++ >> ATENÇÃO <<
# A constante $T2T contém o caminho para o txt2tags e
# deve ser alterada conforme o seu sistema
# Alguns exemplos:
# $T2T = 'python C:/utils/txt2tags.py'
# $T2T = 'E:/utils/txt2tags/txt2tags.exe'
# $T2T = /usr/local/bin/txt2tags
if RUBY_PLATFORM =~ /mswin/
$T2T = 'C:/Arquivos de programas/txt2tags/txt2tags.exe'
$POPEN = true
else
$T2T = 'txt2tags'
$POPEN = true #false
end
$flags = ''
$IDX_SRC = 0 # indice para caminho dos fontes
$IDX_DSTDIR = 1 # indice para caminho dos destinos
$IDX_DSTFILE = 2 # indice para nome do arquivo destino
# Tipos válidos para o txt2tags
$tipos = %w(html xhtml sgml tex man mgp moin pm6 txt)
# Mostra uma mensagem de erro e aborta o programa
# ---
def abort(msg)
puts "Abnormal program termination!"
puts msg
exit
end
# Retorna uma string com a versão do programa
# ---
def version
print "\nt2tmake.rb version #{$VERSAO}\n"
print "(c) 2003 by Guaracy B. Monteiro\n\n"
end
# Pesquisa um diretório e executa um bloco passado para
# cada arquivo que coincidir com a máscara especificada
# Se _recursive_ for igual a +verdadeiro+, a pesquisa
# será efetuada em toda a árvore do diretório informado
#---
def dir_recurse(dirname, mask, recursive, &action)
d = Dir.pwd
Dir.chdir(dirname)
Dir["#{mask}"].each do |file|
action.call("#{dirname}/#{file}")
end
return if !recursive
Dir.open(dirname) do |dir|
dir.each do |file|
if FileTest.directory?("#{dirname}/#{file}")
next if file =~ /^\.\.?$/
dir_recurse("#{dirname}/#{file}", mask, recursive, &action)
end
end
end
Dir.chdir(d)
end
# Recebe uma matriz com o caminho completo e nome dos
# arquivos, a especificação do diretório original, a
# especificação do diretório destino e o tipo (extensão)
# dos arquivos destinos.
# Retorna uma matriz onde cada elemento contém:
# - caminho completo e nome dos arquivos de origem
# - caminho completo do destino
# - nome e extensão do arquivo destino correspondente
# ---
def gen_destfiles(files, srcdir, dst_dir, type)
basedir = srcdir.size
files.collect do |filedir|
dir = dst_dir + File.dirname(filedir)[basedir..-1]
file = File.basename(filedir,'.t2t')
if !@l10n.nil?
if type == 'html' and file =~ /^index\-/
file = file.split('-',2)
file = sprintf("%s.%s.%s", file[0] , type, file[1])
else
file << ".#{type}"
end
else
file << ".#{type}"
end
[filedir, dir, file]
end
end
# Rotina para a verificar se o arquivo fonte é mais
# atual que o arquivo destino ou se este não existe.
# Se for confirmada a condição, o programa executará
# o txt2tags para que a atualização do destino seja
# feita, bem como irá gravar no arquivo +logfile+ o
# caminho completo e nome do arquivo destino que
# foi alterado.
# ---
def make(files, logfile)
if !@log_fn.nil?
logfile = File.new(logfile,"a")
logfile.puts Time.new.strftime("# %c\n")
end
files.each do |data|
src = data[$IDX_SRC]
dstdir = data[$IDX_DSTDIR]
dst = "#{dstdir}/#{data[$IDX_DSTFILE]}"
begin
if !FileTest.exist?(dstdir)
FileUtils.mkdir_p(dstdir)
end
rescue => erro
abort("Can't create directory - #{dstdir}")
end
if !@all.nil? or !File.exist?(dst) or File.stat(src).mtime > File.stat(dst).mtime
puts "Processing - #{src}"
cmd = "\"#{$T2T}\" #{$flags} -o \"#{dst}\" \"#{src}\""
if $POPEN
IO.popen(cmd) { |res|
puts res.readlines
}
else
if !system(cmd)
abort("Error while executin - '#{$T2T}'")
end
end
logfile.puts dst if !@log_fn.nil?
else
puts"Nothing to be done for - #{data[$IDX_DSTFILE]} #{src}"
end
end
end
# Remove todos os arquivos com uma determinada
# extensão em um diretório destino baseado em
# uma lista de arquivos fontes especificadas
# ---
def clean(files, type, dst_dir)
puts "Cleaning..."
files.each do |data|
dst = "#{data[$IDX_DSTDIR]}/#{data[$IDX_DSTFILE]}"
if File.exist?(dst)
puts "deleting - #{dst}"
File.delete(dst)
end
end
end
# Mostra rótulos válidos em arquivo batch e encerra
# ---
def abort_batch_labels(conf_file, data, msg)
puts msg unless msg.empty?
puts "Valid labels for #{conf_file}:"
data.each do |line|
puts "#{line}" if line =~ /^\[.+\]\s*/
end
exit
end
# Pocessamento de arquivos com instruções
# ---
def batch(file,label,msg="")
conf_file = File.expand_path(file)
conf_file += "/t2t-make.conf" if FileTest.directory?(conf_file)
if !FileTest.exist?(conf_file)
puts "Can't find file #{conf_file}"
exit
end
data = IO.readlines(conf_file)
data.collect! do |linha| linha.chop end
if label.nil?
abort_batch_labels(conf_file,data,msg)
end
idx = data.index("[#{label}]")
if idx.nil?
abort_batch_labels(conf_file,data,"Can't find label - '#{label}'")
end
for i in (idx+1)..(data.size-1)
break if data[i] == ''
abort("Malformated line\nfile : #{conf_file}\nlabel : [#{label}]\nline - #{data[i]}\nin") if data[i] !~ /^\-/
ARGV << data[i].split(nil,2)
end
ARGV.flatten!
end
# Rotina principal do programa, encarregada de verificar
# os argumentos especificados na linha de comando.
# ---
def parse_args
ARGV.options do
|opts|
opts.on_tail
opts.on_tail("common options:")
opts.on_tail("-h", "--help", "show this message") do
puts opts
exit
end
opts.on_tail("-V", "--version", "show version") do
puts "t2tmake #{$VERSION}"
exit
end
opts.on_head("specific options:")
opts.on("-t", "--type=TARGET", String, "set target (txt2tags) document type",$tipos.join(",")) do |x|@type=x
if !@type.nil?
if !$tipos.include?(@type)
puts "'#{@type}' is not a valid target type. Valid types are:"
puts $tipos.join(' | ')
exit
end
end
end
# formal argument cannot be an instance variable: {|@ext|}
opts.on("-e", "--ext=EXT", String, "set output file extension") {|x|@ext=x}
opts.on("-r", "--recusive", "recursive directory processing.") {|x|@recursive=x}
opts.on("-s", "--sdir=DIR", String, "especify source directory","default => actual_directory (pwd)") {|x|@src_dir=x}
opts.on("-d", "--ddir=DIR", String, "set target directory","default => actual_directory./_<type>") {|x|@dst_dir=x}
opts.on("-l", "--log[=FILE]", "log changes (processed files)","default => target_directory/t2tmake.log") {|x|@log_fn=x;@log_fn ||= ''}
opts.on("--L10N", "Apache localization", "index-en.t2t => index.html.en") {|x|@l10n=x}
opts.on("-a", "--all", "force to process all files") {|x|@all=x}
opts.on("-c", "--clean", "erase all target files before processing") {|x|@clean=x}
opts.on("-b", "--batch=FILE[,LABEL]",Array,"use options from an specified 'label'","stored in a batch file;","without LABEL, list all labels") do |x,y|@batch,@label=x,y
if @label.nil?
batch(@batch,@label,"No label specified.")
exit
end
end
opts.parse!
end
end
# Verificar a validade dos argumentos passados para o programa
# e toma as providencias necessárias como ajustar nomes de
# diretórios, montar a lista de arquivos e chamar o método
# responsável para execução dos procedimentos desejados pelo
# usuário.
# ---
def main
# warning: instance variable @foo not initialized
@batch = nil
@type = nil
@src_dir = nil
@dst_dir = nil
@ext = nil
@recursive = nil
@clean = nil
@log_fn = nil
@log_fn = nil
# if ARGV.empty?
# ARGV.push("--help")
# end
fbatch = false
while true do
parse_args
if !@batch.nil?
abort("Nested batch files not allowed.") if fbatch
ARGV.clear
batch(@batch,@label)
@batch=nil
fbatch = true
next
else
break
end
end
@type='html' if @type.nil?
if @src_dir.nil?
src_dir = Dir.pwd
else
src_dir = @src_dir.gsub(/[\"\']/,'')
src_dir = File.expand_path(src_dir)
end
if @dst_dir.nil?
dst_dir = src_dir + "/_#{@type}"
else
dst_dir = @dst_dir.gsub(/[\"\']/,'')
dst_dir = File.expand_path(dst_dir)
end
if !FileTest.exist?(dst_dir)
FileUtils.mkdir_p(dst_dir)
end
files = []
ext = (@ext.nil?) ? (@type) : (@ext)
dir_recurse(src_dir, "*.t2t", !@recursive.nil?) { |file| files << file }
files = gen_destfiles(files, src_dir, dst_dir, ext)
if !@clean.nil?
clean(files, type, dst_dir)
return
end
if !@log_fn.nil?
logfile = (@log_fn.empty?) ? ("#{dst_dir}/t2tmake.log") : (File.expand_path(@log_fn))
if !FileTest.exist?(File.dirname(logfile))
begin
Dir.mkdir("#{File.dirname(logfile)}")
rescue => erro
abort("#{erro}\nCan't create logfile - #{logfile}")
end
end
else
logfile = ""
end
make(files, "#{logfile}")
end
=begin
#clean não usa log
$flags = $flags + "-t #{$OPT_type} "
end
=end
# inicio do programa
main
puts "Done."