bookbindery 2.1.5 → 3.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/bookbinder.rb +0 -4
- data/lib/bookbinder/cf_command_runner.rb +11 -5
- data/lib/bookbinder/cli.rb +8 -12
- data/lib/bookbinder/colorizer.rb +1 -2
- data/lib/bookbinder/command_runner.rb +0 -2
- data/lib/bookbinder/commands/bind.rb +96 -99
- data/lib/bookbinder/commands/bind/directory_preparer.rb +60 -0
- data/lib/bookbinder/commands/build_and_push_tarball.rb +5 -4
- data/lib/bookbinder/commands/push_from_local.rb +56 -2
- data/lib/bookbinder/commands/push_to_prod.rb +6 -2
- data/lib/bookbinder/commands/tag.rb +15 -3
- data/lib/bookbinder/config/aws_credentials.rb +21 -0
- data/lib/bookbinder/config/cf_credentials.rb +87 -0
- data/lib/bookbinder/configuration.rb +4 -140
- data/lib/bookbinder/configuration_fetcher.rb +28 -4
- data/lib/bookbinder/configuration_validator.rb +11 -164
- data/lib/bookbinder/distributor.rb +16 -12
- data/lib/bookbinder/{dita_to_html_converter.rb → dita_command_creator.rb} +5 -17
- data/lib/bookbinder/dita_preprocessor.rb +14 -12
- data/lib/bookbinder/git_accessor.rb +21 -2
- data/lib/bookbinder/git_hub_repository.rb +0 -43
- data/lib/bookbinder/ingest/cloner_factory.rb +5 -4
- data/lib/bookbinder/ingest/destination_directory.rb +15 -0
- data/lib/bookbinder/ingest/git_hub_repository_cloner.rb +22 -13
- data/lib/bookbinder/ingest/local_filesystem_cloner.rb +38 -14
- data/lib/bookbinder/ingest/working_copy.rb +31 -0
- data/lib/bookbinder/local_dita_section_gatherer.rb +4 -3
- data/lib/bookbinder/local_file_system_accessor.rb +1 -4
- data/lib/bookbinder/middleman_runner.rb +22 -26
- data/lib/bookbinder/remote_yaml_credential_provider.rb +10 -10
- data/lib/bookbinder/repositories/command_repository.rb +18 -12
- data/lib/bookbinder/repositories/section_repository.rb +8 -8
- data/lib/bookbinder/server_director.rb +16 -33
- data/lib/bookbinder/sheller.rb +33 -7
- data/lib/bookbinder/spider.rb +3 -0
- data/lib/bookbinder/streams/switchable_stdout_and_red_stderr.rb +38 -0
- data/lib/bookbinder/terminal.rb +11 -1
- data/lib/bookbinder/validation_checkers/archive_menu_checker.rb +31 -0
- data/lib/bookbinder/validation_checkers/config_version_checker.rb +91 -0
- data/lib/bookbinder/validation_checkers/dita_section_checker.rb +20 -0
- data/lib/bookbinder/validation_checkers/duplicate_section_name_checker.rb +25 -0
- data/lib/bookbinder/validation_checkers/repository_name_presence_checker.rb +33 -0
- data/lib/bookbinder/validation_checkers/required_keys_checker.rb +43 -0
- data/lib/bookbinder/values/dita_section.rb +5 -1
- data/lib/bookbinder/values/output_locations.rb +25 -2
- data/lib/bookbinder/values/user_message.rb +2 -2
- data/master_middleman/bookbinder_helpers.rb +5 -15
- data/template_app/Gemfile.lock +1 -1
- metadata +60 -80
- data/lib/bookbinder/commands/generate_pdf.rb +0 -141
- data/lib/bookbinder/pdf_generator.rb +0 -73
- data/lib/bookbinder/publisher.rb +0 -58
- data/lib/bookbinder/user_message_presenter.rb +0 -21
@@ -1,141 +0,0 @@
|
|
1
|
-
require_relative '../pdf_generator'
|
2
|
-
require_relative '../server_director'
|
3
|
-
require_relative 'bookbinder_command'
|
4
|
-
require_relative 'naming'
|
5
|
-
|
6
|
-
module Bookbinder
|
7
|
-
module Commands
|
8
|
-
class GeneratePDF < BookbinderCommand
|
9
|
-
include Commands::Naming
|
10
|
-
|
11
|
-
class AppNotPublished < StandardError
|
12
|
-
def initialize(msg='You must publish locally before you generate a PDF.')
|
13
|
-
super(msg)
|
14
|
-
end
|
15
|
-
end
|
16
|
-
|
17
|
-
class PDFConfigMissing < StandardError
|
18
|
-
def initialize(file)
|
19
|
-
super("PDF config file '#{file}' does not exist.")
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
|
-
class PDFOptionMissing < StandardError
|
24
|
-
def initialize(msg='No PDF options provided in config.yml')
|
25
|
-
super(msg)
|
26
|
-
end
|
27
|
-
end
|
28
|
-
|
29
|
-
class IncompletePDFConfig < StandardError
|
30
|
-
def initialize(file:nil, key:nil)
|
31
|
-
super("#{file} is missing required key '#{key}'")
|
32
|
-
end
|
33
|
-
end
|
34
|
-
|
35
|
-
def usage
|
36
|
-
["generate_pdf [<file_name>.yml]",
|
37
|
-
"Generate a PDF from the files specified in <file_name.yml>"]
|
38
|
-
end
|
39
|
-
|
40
|
-
def run(params)
|
41
|
-
raise AppNotPublished unless Dir.exists?('final_app')
|
42
|
-
|
43
|
-
@pdf_config_file = find_pdf_config_file(params)
|
44
|
-
|
45
|
-
ServerDirector.new(@logger, directory: 'final_app').use_server { |port| capture_pages_into_pdf_at(port) }
|
46
|
-
0
|
47
|
-
end
|
48
|
-
|
49
|
-
def find_pdf_config_file(params)
|
50
|
-
if params.first
|
51
|
-
pdf_config_file = File.expand_path(params.first)
|
52
|
-
raise PDFConfigMissing, File.basename(pdf_config_file) unless File.exists?(pdf_config_file)
|
53
|
-
pdf_config_file
|
54
|
-
else
|
55
|
-
@logger.warn "Declaring PDF options in config.yml is deprecated.\nDeclare them in a PDF config file, instead, and target that file when you re-invoke bookbinder.\ne.g. bookbinder generate_pdf theGoodParts.yml"
|
56
|
-
end
|
57
|
-
end
|
58
|
-
|
59
|
-
private
|
60
|
-
|
61
|
-
def capture_pages_into_pdf_at(port)
|
62
|
-
local_host = "localhost:#{port}"
|
63
|
-
header = pdf_options.fetch('header') { raise IncompletePDFConfig, {file: @pdf_config_file, key: :header} }
|
64
|
-
|
65
|
-
output_filename = get_output_file_name
|
66
|
-
urls_to_capture = get_urls_to_capture(local_host)
|
67
|
-
|
68
|
-
PdfGenerator.new(@logger).generate(urls_to_capture, output_filename, "http://#{local_host}/#{header}", pdf_options['copyright_notice'])
|
69
|
-
end
|
70
|
-
|
71
|
-
def pdf_options
|
72
|
-
@pdf_options ||= @pdf_config_file ? YAML.load(File.read(@pdf_config_file)) : main_config_pdf_options
|
73
|
-
end
|
74
|
-
|
75
|
-
def main_config_pdf_options
|
76
|
-
raise PDFOptionMissing unless config.has_option?('pdf')
|
77
|
-
{
|
78
|
-
'filename' => config.pdf.fetch('filename'),
|
79
|
-
'header' => config.pdf.fetch('header')
|
80
|
-
}
|
81
|
-
end
|
82
|
-
|
83
|
-
def get_output_file_name
|
84
|
-
if @pdf_config_file
|
85
|
-
File.basename(@pdf_config_file).gsub(/yml/, 'pdf')
|
86
|
-
else
|
87
|
-
pdf_options.fetch('filename')
|
88
|
-
end
|
89
|
-
end
|
90
|
-
|
91
|
-
def get_urls_to_capture(local_host)
|
92
|
-
if @pdf_config_file
|
93
|
-
pages = pdf_options.fetch('pages')
|
94
|
-
return expand_urls(pages, local_host) if any_include_wildcard?(pages)
|
95
|
-
pages.map { |l| "http://#{local_host}/#{l}" }
|
96
|
-
else
|
97
|
-
sitemap_links(local_host)
|
98
|
-
end
|
99
|
-
end
|
100
|
-
|
101
|
-
def any_include_wildcard?(pages)
|
102
|
-
pages.each do |page|
|
103
|
-
return true if page.include?('*')
|
104
|
-
end
|
105
|
-
false
|
106
|
-
end
|
107
|
-
|
108
|
-
def expand_urls(pages, local_host)
|
109
|
-
final_pages = []
|
110
|
-
pages.each do |page|
|
111
|
-
if page.include?('*')
|
112
|
-
matching_pages = find_matching_files_in_directory(page, local_host)
|
113
|
-
final_pages += matching_pages
|
114
|
-
else
|
115
|
-
final_pages << "http://#{local_host}/#{page}"
|
116
|
-
end
|
117
|
-
end
|
118
|
-
final_pages
|
119
|
-
end
|
120
|
-
|
121
|
-
def find_matching_files_in_directory(wildcard_page, local_host)
|
122
|
-
wildcard_path = wildcard_page.gsub('*','')
|
123
|
-
possible_links = sitemap_links(local_host)
|
124
|
-
possible_links.select { |link| URI(link).path.match(/^\/#{Regexp.escape(wildcard_path)}/)}
|
125
|
-
end
|
126
|
-
|
127
|
-
def sitemap_links(local_host)
|
128
|
-
raw_links = Nokogiri::XML(sitemap).css('loc').map &:inner_html
|
129
|
-
deployed_host = URI(raw_links[0]).host
|
130
|
-
|
131
|
-
deployed_host ?
|
132
|
-
raw_links.map { |l| l.gsub(/#{Regexp.escape(deployed_host)}/, local_host) } :
|
133
|
-
raw_links.map { |l| "http://#{local_host}/#{l}" }
|
134
|
-
end
|
135
|
-
|
136
|
-
def sitemap
|
137
|
-
File.read File.join('public', 'sitemap.xml')
|
138
|
-
end
|
139
|
-
end
|
140
|
-
end
|
141
|
-
end
|
@@ -1,73 +0,0 @@
|
|
1
|
-
require 'net/http'
|
2
|
-
|
3
|
-
module Bookbinder
|
4
|
-
class PdfGenerator
|
5
|
-
class MissingSource < StandardError
|
6
|
-
def initialize(required_file)
|
7
|
-
super "Could not find file #{required_file}"
|
8
|
-
end
|
9
|
-
end
|
10
|
-
|
11
|
-
def initialize(logger)
|
12
|
-
@logger = logger
|
13
|
-
end
|
14
|
-
|
15
|
-
def generate(sources, target, header, left_footer=nil)
|
16
|
-
sources.each { |s| check_destination_exists s }
|
17
|
-
check_destination_exists header
|
18
|
-
|
19
|
-
left_footer ||= " © Copyright 2013-#{Time.now.year}, Pivotal"
|
20
|
-
|
21
|
-
toc_xslt_path = File.expand_path('../../../toc.xslt', __FILE__)
|
22
|
-
|
23
|
-
command = <<-CMD
|
24
|
-
wkhtmltopdf \
|
25
|
-
--enable-external-links \
|
26
|
-
--disable-javascript \
|
27
|
-
--load-error-handling ignore \
|
28
|
-
--margin-top 26mm \
|
29
|
-
--margin-bottom 13mm \
|
30
|
-
--header-spacing 10 \
|
31
|
-
--header-html #{header} \
|
32
|
-
--footer-spacing 5 \
|
33
|
-
--footer-font-size 10 \
|
34
|
-
--footer-left '#{left_footer}' \
|
35
|
-
--footer-center '[page] of [toPage]' \
|
36
|
-
--print-media-type \
|
37
|
-
toc --xsl-style-sheet #{toc_xslt_path} \
|
38
|
-
#{sources.join(' ')} \
|
39
|
-
#{target}
|
40
|
-
CMD
|
41
|
-
|
42
|
-
`#{command}`
|
43
|
-
|
44
|
-
raise "'wkhtmltopdf' appears to have failed" unless $?.success? && File.exist?(target)
|
45
|
-
|
46
|
-
@logger.log "\nYour PDF file was generated to #{target.green}"
|
47
|
-
|
48
|
-
end
|
49
|
-
|
50
|
-
def check_file_exists(required_file)
|
51
|
-
unless File.exist? required_file
|
52
|
-
@logger.error "\nPDF Generation failed (could not find file)!"
|
53
|
-
raise MissingSource, required_file
|
54
|
-
end
|
55
|
-
end
|
56
|
-
|
57
|
-
def check_destination_exists(url)
|
58
|
-
uri = URI(url)
|
59
|
-
if uri.class == URI::Generic
|
60
|
-
check_file_exists url
|
61
|
-
elsif uri.class == URI::HTTP
|
62
|
-
check_url_exists url
|
63
|
-
else
|
64
|
-
@logger.error "Malformed destination provided for PDF generation source: #{url}"
|
65
|
-
end
|
66
|
-
end
|
67
|
-
|
68
|
-
def check_url_exists(url)
|
69
|
-
res = Net::HTTP.get_response(URI(url))
|
70
|
-
raise MissingSource, url if res.code == '404'
|
71
|
-
end
|
72
|
-
end
|
73
|
-
end
|
data/lib/bookbinder/publisher.rb
DELETED
@@ -1,58 +0,0 @@
|
|
1
|
-
require 'middleman-syntax'
|
2
|
-
require_relative 'deprecated_logger'
|
3
|
-
require_relative 'directory_helpers'
|
4
|
-
require_relative 'repositories/section_repository'
|
5
|
-
|
6
|
-
module Bookbinder
|
7
|
-
class Publisher
|
8
|
-
include DirectoryHelperMethods
|
9
|
-
|
10
|
-
def initialize(logger, sitemap_writer, static_site_generator, file_system_accessor)
|
11
|
-
@logger = logger
|
12
|
-
@sitemap_writer = sitemap_writer
|
13
|
-
@static_site_generator = static_site_generator
|
14
|
-
@file_system_accessor = file_system_accessor
|
15
|
-
end
|
16
|
-
|
17
|
-
def publish(subnavs, cli_options, output_paths, publish_config)
|
18
|
-
intermediate_directory = output_paths.output_dir
|
19
|
-
final_app_dir = output_paths.final_app_dir
|
20
|
-
master_dir = File.join intermediate_directory, 'master_middleman'
|
21
|
-
workspace_dir = File.join master_dir, 'source'
|
22
|
-
build_directory = File.join master_dir, 'build/.'
|
23
|
-
public_directory = File.join final_app_dir, 'public'
|
24
|
-
|
25
|
-
FileUtils.cp 'redirects.rb', final_app_dir if File.exists?('redirects.rb')
|
26
|
-
|
27
|
-
host_for_sitemap = publish_config.fetch(:host_for_sitemap)
|
28
|
-
|
29
|
-
generate_site(cli_options, output_paths, publish_config, master_dir, workspace_dir, subnavs, build_directory, public_directory)
|
30
|
-
result = generate_sitemap(host_for_sitemap)
|
31
|
-
|
32
|
-
@logger.log "Bookbinder bound your book into #{final_app_dir.to_s.green}"
|
33
|
-
|
34
|
-
!result.has_broken_links?
|
35
|
-
end
|
36
|
-
|
37
|
-
private
|
38
|
-
|
39
|
-
attr_reader :section_repository, :logger, :file_system_accessor, :sitemap_writer
|
40
|
-
|
41
|
-
def generate_sitemap(host_for_sitemap)
|
42
|
-
raise "Your public host must be a single String." unless host_for_sitemap.is_a?(String)
|
43
|
-
sitemap_writer.write(host_for_sitemap)
|
44
|
-
end
|
45
|
-
|
46
|
-
def generate_site(cli_options, output_paths, publish_config, middleman_dir, workspace_dir, subnavs, build_dir, public_dir)
|
47
|
-
@static_site_generator.run(middleman_dir,
|
48
|
-
workspace_dir,
|
49
|
-
publish_config.fetch(:template_variables, {}),
|
50
|
-
output_paths.local_repo_dir,
|
51
|
-
cli_options[:verbose],
|
52
|
-
subnavs,
|
53
|
-
publish_config[:host_for_sitemap],
|
54
|
-
publish_config[:archive_menu])
|
55
|
-
file_system_accessor.copy build_dir, public_dir
|
56
|
-
end
|
57
|
-
end
|
58
|
-
end
|
@@ -1,21 +0,0 @@
|
|
1
|
-
require_relative 'colorizer'
|
2
|
-
|
3
|
-
module Bookbinder
|
4
|
-
class UserMessagePresenter
|
5
|
-
def initialize(colorizer)
|
6
|
-
@colorizer = colorizer
|
7
|
-
end
|
8
|
-
|
9
|
-
def get_error(user_message)
|
10
|
-
colorizer.colorize(user_message.message, Colorizer::Colors.red)
|
11
|
-
end
|
12
|
-
|
13
|
-
def get_warning(user_message)
|
14
|
-
colorizer.colorize(user_message.message, Colorizer::Colors.yellow)
|
15
|
-
end
|
16
|
-
|
17
|
-
private
|
18
|
-
|
19
|
-
attr_reader :colorizer
|
20
|
-
end
|
21
|
-
end
|