asciidoctor-kroki 0.6.0 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 1d98287cf9a15751a442de9b1a07565c097206aae0912ca204ecaf4bdede4020
4
- data.tar.gz: b1252225ed15a9f093d8a3c1d577e2bfa23c2abe7962981d638f49ea81d90a7b
3
+ metadata.gz: 46f326afecfa57d4b918121fdf939c2c8dcf46897daeff74236a551628ffbfdf
4
+ data.tar.gz: c43629e9e6d4303fa59d761b61e95e6b63006cea1a27faf1dc3e80ceb9994f8c
5
5
  SHA512:
6
- metadata.gz: 46688eb160c567e33ba1f220ab229848a66874af0713962c339bc4d3b7d3352a5ef3f2f74e9c257bae6c579e03bf6c32cdf55e16f9b64d7b189aa103bf2d8550
7
- data.tar.gz: 78a231f8b5921330aab30a2cd5c4f56ab84f917e31dc4cc85d2eb126cec84f04bd52756db2ff1fd8991116086b1100184c0644f35929fadb8ae49f95806e1248
6
+ metadata.gz: 70eac4468da00da494aa490e3c413189feb13474d25aa778f1d0cb301957c7ce1811bbc82cc7d1e2782a43223452f5b1de75a150b446824c2de7f9380811defc
7
+ data.tar.gz: e9d6cbbdc63c8f28dd99c1921f1496765ccbb873210756c765d879d1311994243af42f55f3d4dc18e0500be299ef89d5027bbccf5afefee24255d65c71e829d4
data/Gemfile.lock CHANGED
@@ -1,13 +1,13 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- asciidoctor-kroki (0.6.0)
4
+ asciidoctor-kroki (0.7.0)
5
5
  asciidoctor (~> 2.0)
6
6
 
7
7
  GEM
8
8
  remote: https://rubygems.org/
9
9
  specs:
10
- asciidoctor (2.0.11)
10
+ asciidoctor (2.0.17)
11
11
  ast (2.4.2)
12
12
  diff-lcs (1.4.4)
13
13
  parallel (1.22.1)
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require 'cgi'
3
4
  require 'asciidoctor/extensions' unless RUBY_ENGINE == 'opal'
4
5
 
5
6
  # Asciidoctor extensions
@@ -137,6 +138,7 @@ module AsciidoctorExtensions
137
138
  include Asciidoctor::Logging
138
139
 
139
140
  TEXT_FORMATS = %w[txt atxt utxt].freeze
141
+ BUILTIN_ATTRIBUTES = %w[target width height format fallback link float align role caption title cloaked-context subs].freeze
140
142
 
141
143
  class << self
142
144
  # rubocop:disable Metrics/AbcSize
@@ -148,13 +150,12 @@ module AsciidoctorExtensions
148
150
  if (subs = attrs['subs'])
149
151
  diagram_text = parent.apply_subs(diagram_text, parent.resolve_subs(subs))
150
152
  end
151
- title = attrs.delete('title')
152
- caption = attrs.delete('caption')
153
153
  attrs.delete('opts')
154
154
  format = get_format(doc, attrs, diagram_type)
155
155
  attrs['role'] = get_role(format, attrs['role'])
156
156
  attrs['format'] = format
157
- kroki_diagram = KrokiDiagram.new(diagram_type, format, diagram_text, attrs['target'])
157
+ opts = attrs.filter { |key, _| key.is_a?(String) && BUILTIN_ATTRIBUTES.none? { |k| key == k } && !key.end_with?('-option') }
158
+ kroki_diagram = KrokiDiagram.new(diagram_type, format, diagram_text, attrs['target'], opts)
158
159
  kroki_client = KrokiClient.new({
159
160
  server_url: server_url(doc),
160
161
  http_method: http_method(doc),
@@ -162,11 +163,14 @@ module AsciidoctorExtensions
162
163
  source_location: doc.reader.cursor_at_mark,
163
164
  http_client: KrokiHttpClient
164
165
  }, logger)
166
+ alt = get_alt(attrs)
167
+ title = attrs.delete('title')
168
+ caption = attrs.delete('caption')
165
169
  if TEXT_FORMATS.include?(format)
166
170
  text_content = kroki_client.text_content(kroki_diagram)
167
171
  block = processor.create_block(parent, 'literal', text_content, attrs)
168
172
  else
169
- attrs['alt'] = get_alt(attrs)
173
+ attrs['alt'] = alt
170
174
  attrs['target'] = create_image_src(doc, kroki_diagram, kroki_client)
171
175
  block = processor.create_image_block(parent, attrs)
172
176
  end
@@ -221,8 +225,8 @@ module AsciidoctorExtensions
221
225
  if format == 'png'
222
226
  # redirect PNG format to SVG if the diagram library only supports SVG as output format.
223
227
  # this is useful when the default format has been set to PNG
224
- # Currently, mermaid, nomnoml, svgbob, wavedrom only support SVG as output format.
225
- svg_only_diagram_types = %i[mermaid nomnoml svgbob wavedrom]
228
+ # Currently, nomnoml, svgbob, wavedrom only support SVG as output format.
229
+ svg_only_diagram_types = %i[nomnoml svgbob wavedrom]
226
230
  format = 'svg' if svg_only_diagram_types.include?(diagram_type)
227
231
  end
228
232
  format
@@ -269,17 +273,19 @@ module AsciidoctorExtensions
269
273
  require 'zlib'
270
274
  require 'digest'
271
275
 
272
- attr_reader :type, :text, :format, :target
276
+ attr_reader :type, :text, :format, :target, :opts
273
277
 
274
- def initialize(type, format, text, target = nil)
278
+ def initialize(type, format, text, target = nil, opts = {})
275
279
  @text = text
276
280
  @type = type
277
281
  @format = format
278
282
  @target = target
283
+ @opts = opts
279
284
  end
280
285
 
281
286
  def get_diagram_uri(server_url)
282
- _join_uri_segments(server_url, @type, @format, encode)
287
+ query_params = opts.map { |k, v| "#{k}=#{_url_encode(v.to_s)}" }.join('&') unless opts.empty?
288
+ _join_uri_segments(server_url, @type, @format, encode) + (query_params ? "?#{query_params}" : '')
283
289
  end
284
290
 
285
291
  def encode
@@ -308,6 +314,10 @@ module AsciidoctorExtensions
308
314
 
309
315
  private
310
316
 
317
+ def _url_encode(text)
318
+ CGI.escape(text).gsub(/\+/, '%20')
319
+ end
320
+
311
321
  def _join_uri_segments(base, *uris)
312
322
  segments = []
313
323
  # remove trailing slashes
@@ -354,6 +364,7 @@ module AsciidoctorExtensions
354
364
  type = kroki_diagram.type
355
365
  format = kroki_diagram.format
356
366
  text = kroki_diagram.text
367
+ opts = kroki_diagram.opts
357
368
  if @method == 'adaptive' || @method == 'get'
358
369
  uri = kroki_diagram.get_diagram_uri(server_url)
359
370
  if uri.length > @max_uri_length
@@ -361,15 +372,15 @@ module AsciidoctorExtensions
361
372
  if @method == 'get'
362
373
  # The request might be rejected by the server with a 414 Request-URI Too Large.
363
374
  # Consider using the attribute kroki-http-method with the value 'adaptive'.
364
- @http_client.get(uri, encoding)
375
+ @http_client.get(uri, opts, encoding)
365
376
  else
366
- @http_client.post("#{@server_url}/#{type}/#{format}", text, encoding)
377
+ @http_client.post("#{@server_url}/#{type}/#{format}", text, opts, encoding)
367
378
  end
368
379
  else
369
- @http_client.get(uri, encoding)
380
+ @http_client.get(uri, opts, encoding)
370
381
  end
371
382
  else
372
- @http_client.post("#{@server_url}/#{type}/#{format}", text, encoding)
383
+ @http_client.post("#{@server_url}/#{type}/#{format}", text, opts, encoding)
373
384
  end
374
385
  end
375
386
  end
@@ -384,10 +395,11 @@ module AsciidoctorExtensions
384
395
  class << self
385
396
  REFERER = "asciidoctor/kroki.rb/#{Asciidoctor::AsciidoctorKroki::VERSION}"
386
397
 
387
- def get(uri, _)
398
+ def get(uri, opts, _)
388
399
  uri = URI(uri)
389
- request = ::Net::HTTP::Get.new(uri)
390
- request['referer'] = REFERER
400
+ headers = opts.transform_keys { |key| "Kroki-Diagram-Options-#{key}" }
401
+ .merge({ 'referer' => REFERER })
402
+ request = ::Net::HTTP::Get.new(uri, headers)
391
403
  ::Net::HTTP.start(
392
404
  uri.hostname,
393
405
  uri.port,
@@ -397,12 +409,16 @@ module AsciidoctorExtensions
397
409
  end
398
410
  end
399
411
 
400
- def post(uri, data, _)
412
+ def post(uri, data, opts, _)
413
+ headers = opts.transform_keys { |key| "Kroki-Diagram-Options-#{key}" }
414
+ .merge({
415
+ 'Content-Type' => 'text/plain',
416
+ 'referer' => REFERER
417
+ })
401
418
  res = ::Net::HTTP.post(
402
419
  URI(uri),
403
420
  data,
404
- 'Content-Type' => 'text/plain',
405
- 'Referer' => REFERER
421
+ headers
406
422
  )
407
423
  res.body
408
424
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Asciidoctor
4
4
  module AsciidoctorKroki
5
- VERSION = '0.6.0'
5
+ VERSION = '0.7.0'
6
6
  end
7
7
  end
@@ -37,18 +37,19 @@ describe ::AsciidoctorExtensions::KrokiClient do
37
37
  "GET #{uri}"
38
38
  end
39
39
 
40
- def post(uri, data, _)
40
+ def post(uri, data, _, _)
41
41
  "POST #{uri} - #{data}"
42
42
  end
43
43
  end
44
44
  end
45
45
  kroki_diagram = Class.new do
46
- attr_reader :type, :text, :format
46
+ attr_reader :type, :text, :format, :opts
47
47
 
48
- def initialize(type, format, text)
48
+ def initialize(type, format, text, opts = {})
49
49
  @text = text
50
50
  @type = type
51
51
  @format = format
52
+ @opts = opts
52
53
  end
53
54
 
54
55
  def get_diagram_uri(_)
@@ -62,22 +63,23 @@ describe ::AsciidoctorExtensions::KrokiClient do
62
63
  it 'should get an image with GET request if the URI length is lower or equals than the value configured' do
63
64
  kroki_http_client = Class.new do
64
65
  class << self
65
- def get(uri, _)
66
+ def get(uri, _, _)
66
67
  "GET #{uri}"
67
68
  end
68
69
 
69
- def post(uri, data, _)
70
+ def post(uri, data, _, _)
70
71
  "POST #{uri} - #{data}"
71
72
  end
72
73
  end
73
74
  end
74
75
  kroki_diagram = Class.new do
75
- attr_reader :type, :text, :format
76
+ attr_reader :type, :text, :format, :opts
76
77
 
77
- def initialize(type, format, text)
78
+ def initialize(type, format, text, opts = {})
78
79
  @text = text
79
80
  @type = type
80
81
  @format = format
82
+ @opts = opts
81
83
  end
82
84
 
83
85
  def get_diagram_uri(_)
@@ -20,6 +20,24 @@ describe ::AsciidoctorExtensions::KrokiDiagram do
20
20
  diagram_uri = kroki_diagram.get_diagram_uri('https://my-server/kroki//')
21
21
  expect(diagram_uri).to eq('https://my-server/kroki/vegalite/png/eNqrrgUAAXUA-Q==')
22
22
  end
23
+ it 'should compute a diagram URI with query parameters' do
24
+ text = %q{
25
+ .---.
26
+ /-o-/--
27
+ .-/ / /->
28
+ ( * \/
29
+ '-. \
30
+ \ /
31
+ '
32
+ }
33
+ opts = {
34
+ 'stroke-width' => 1,
35
+ 'background' => 'black'
36
+ }
37
+ kroki_diagram = ::AsciidoctorExtensions::KrokiDiagram.new('svgbob', 'png', text, nil, opts)
38
+ diagram_uri = kroki_diagram.get_diagram_uri('http://localhost:8000')
39
+ expect(diagram_uri).to eq('http://localhost:8000/svgbob/png/eNrjUoAAPV1dXT0uCFtfN19XX1eXCyysrwCEunZAjoaCloJCjD5IWF1XD8gEK49R0IdoUwdTAN3kC7U=?stroke-width=1&background=black')
40
+ end
23
41
  it 'should encode a diagram text definition' do
24
42
  kroki_diagram = ::AsciidoctorExtensions::KrokiDiagram.new('plantuml', 'txt', ' alice -> bob: hello')
25
43
  diagram_definition_encoded = kroki_diagram.encode
@@ -18,6 +18,35 @@ describe ::AsciidoctorExtensions::KrokiBlockProcessor do
18
18
  <div class="content">
19
19
  <img src="https://kroki.io/plantuml/svg/eNpLzMlMTlXQtVNIyk-yUshIzcnJBwA9iwZL" alt="Diagram">
20
20
  </div>
21
+ </div>)
22
+ end
23
+ it 'should only pass diagram options as query parameters' do
24
+ input = <<~'ADOC'
25
+ [plantuml,alice-bob,svg,role=sequence,width=100,format=svg,link=https://asciidoc.org/,align=center,float=right,theme=bluegray]
26
+ ....
27
+ alice -> bob: hello
28
+ ....
29
+ ADOC
30
+ output = Asciidoctor.convert(input, standalone: false)
31
+ (expect output).to eql %(<div class="imageblock right text-center sequence kroki-format-svg kroki">
32
+ <div class="content">
33
+ <a class="image" href="https://asciidoc.org/"><img src="https://kroki.io/plantuml/svg/eNpLzMlMTlXQtVNIyk-yUshIzcnJBwA9iwZL?theme=bluegray" alt="alice-bob" width="100"></a>
34
+ </div>
35
+ </div>)
36
+ end
37
+ it 'should use the title attribute as the alt value' do
38
+ input = <<~'ADOC'
39
+ [plantuml,title="Alice saying hello to Bob"]
40
+ ....
41
+ alice -> bob: hello
42
+ ....
43
+ ADOC
44
+ output = Asciidoctor.convert(input, standalone: false)
45
+ (expect output).to eql %(<div class="imageblock kroki">
46
+ <div class="content">
47
+ <img src="https://kroki.io/plantuml/svg/eNpLzMlMTlXQtVNIyk-yUshIzcnJBwA9iwZL" alt="Alice saying hello to Bob">
48
+ </div>
49
+ <div class="title">Figure 1. Alice saying hello to Bob</div>
21
50
  </div>)
22
51
  end
23
52
  it 'should use png if kroki-default-format is set to png' do
@@ -36,16 +65,18 @@ describe ::AsciidoctorExtensions::KrokiBlockProcessor do
36
65
  end
37
66
  it 'should use svg if kroki-default-format is set to png and the diagram type does not support png' do
38
67
  input = <<~'ADOC'
39
- [mermaid]
68
+ [nomnoml]
40
69
  ....
41
- graph TD;
42
- A-->B;
70
+ [Pirate|eyeCount: Int|raid();pillage()|
71
+ [beard]--[parrot]
72
+ [beard]-:>[foul mouth]
73
+ ]
43
74
  ....
44
75
  ADOC
45
76
  output = Asciidoctor.convert(input, attributes: { 'kroki-default-format' => 'png' }, standalone: false)
46
77
  (expect output).to eql %(<div class="imageblock kroki">
47
78
  <div class="content">
48
- <img src="https://kroki.io/mermaid/svg/eNpLL0osyFAIcbHmUlBw1NW1c7IGADLKBKY=" alt="Diagram">
79
+ <img src="https://kroki.io/nomnoml/svg/eNqLDsgsSixJrUmtTHXOL80rsVLwzCupKUrMTNHQtC7IzMlJTE_V0KzhUlCITkpNLEqJ1dWNLkgsKsoviUUSs7KLTssvzVHIzS8tyYjligUAMhEd0g==" alt="Diagram">
49
80
  </div>
50
81
  </div>)
51
82
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: asciidoctor-kroki
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.0
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Guillaume Grossetie
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-06-22 00:00:00.000000000 Z
11
+ date: 2022-09-01 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: asciidoctor