markdown_exec 1.8.2 → 1.8.4
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/CHANGELOG.md +10 -0
- data/Gemfile.lock +1 -1
- data/bin/tab_completion.sh +15 -3
- data/examples/linked1.md +1 -1
- data/examples/linked2.md +4 -0
- data/lib/constants.rb +1 -1
- data/lib/hash_delegator.rb +211 -388
- data/lib/link_history.rb +131 -0
- data/lib/markdown_exec/version.rb +1 -1
- data/lib/markdown_exec.rb +10 -33
- data/lib/mdoc.rb +40 -30
- data/lib/menu.src.yml +5 -2
- data/lib/menu.yml +6 -3
- metadata +3 -2
data/lib/link_history.rb
ADDED
@@ -0,0 +1,131 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# frozen_string_literal: true
|
3
|
+
|
4
|
+
# encoding=utf-8
|
5
|
+
module MarkdownExec
|
6
|
+
class LinkState
|
7
|
+
attr_accessor :block_name, :document_filename,
|
8
|
+
:inherited_block_names, :inherited_lines
|
9
|
+
|
10
|
+
# Initialize the LinkState with keyword arguments for each attribute.
|
11
|
+
# @param block_name [String, nil] the name of the block.
|
12
|
+
# @param document_filename [String, nil] the filename of the document.
|
13
|
+
# @param inherited_block_names [Array<String>, nil] the names of the inherited blocks.
|
14
|
+
# @param inherited_lines [Array<String>, nil] the inherited lines of code.
|
15
|
+
def initialize(block_name: nil, document_filename: nil,
|
16
|
+
inherited_block_names: [], inherited_lines: nil)
|
17
|
+
@block_name = block_name
|
18
|
+
@document_filename = document_filename
|
19
|
+
@inherited_block_names = inherited_block_names
|
20
|
+
@inherited_lines = inherited_lines
|
21
|
+
end
|
22
|
+
|
23
|
+
# Creates an empty LinkState instance.
|
24
|
+
# @return [LinkState] an instance with all attributes set to their default values.
|
25
|
+
def self.empty
|
26
|
+
new
|
27
|
+
end
|
28
|
+
|
29
|
+
# Custom equality method to compare LinkState objects.
|
30
|
+
# @param other [LinkState] the other LinkState object to compare with.
|
31
|
+
# @return [Boolean] true if the objects are equal, false otherwise.
|
32
|
+
def ==(other)
|
33
|
+
other.class == self.class &&
|
34
|
+
other.block_name == block_name &&
|
35
|
+
other.document_filename == document_filename &&
|
36
|
+
other.inherited_block_names == inherited_block_names &&
|
37
|
+
other.inherited_lines == inherited_lines
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
class LinkHistory
|
42
|
+
def initialize
|
43
|
+
@history = []
|
44
|
+
end
|
45
|
+
|
46
|
+
# Peeks at the most recent LinkState, returns an empty LinkState if stack is empty.
|
47
|
+
def peek
|
48
|
+
@history.last || LinkState.empty
|
49
|
+
end
|
50
|
+
|
51
|
+
# Pops the most recent LinkState off the stack, returns an empty LinkState if stack is empty.
|
52
|
+
def pop
|
53
|
+
@history.pop || LinkState.empty
|
54
|
+
end
|
55
|
+
|
56
|
+
def prior_state_exist?
|
57
|
+
peek.document_filename.present?
|
58
|
+
end
|
59
|
+
|
60
|
+
# Pushes a LinkState onto the stack.
|
61
|
+
def push(link_state)
|
62
|
+
@history.push(link_state)
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
if $PROGRAM_NAME == __FILE__
|
68
|
+
require 'bundler/setup'
|
69
|
+
Bundler.require(:default)
|
70
|
+
|
71
|
+
require 'minitest/autorun'
|
72
|
+
require 'mocha/minitest'
|
73
|
+
|
74
|
+
module MarkdownExec
|
75
|
+
class TestLinkHistory < Minitest::Test
|
76
|
+
def setup
|
77
|
+
@link_history = LinkHistory.new
|
78
|
+
@link_state1 = LinkState.new(block_name: 'block1', document_filename: 'document1.txt',
|
79
|
+
inherited_lines: ['code1.rb'])
|
80
|
+
@link_state2 = LinkState.new(block_name: 'block2', document_filename: 'document2.txt',
|
81
|
+
inherited_lines: ['code2.rb'])
|
82
|
+
end
|
83
|
+
|
84
|
+
def test_push
|
85
|
+
@link_history.push(@link_state1)
|
86
|
+
assert_equal @link_state1, @link_history.peek
|
87
|
+
end
|
88
|
+
|
89
|
+
def test_pop
|
90
|
+
@link_history.push(@link_state1)
|
91
|
+
@link_history.push(@link_state2)
|
92
|
+
assert_equal @link_state2, @link_history.pop
|
93
|
+
assert_equal @link_state1, @link_history.peek
|
94
|
+
end
|
95
|
+
|
96
|
+
def test_peek_empty
|
97
|
+
assert_equal LinkState.empty, @link_history.peek
|
98
|
+
end
|
99
|
+
|
100
|
+
def test_pop_empty
|
101
|
+
assert_equal LinkState.empty, @link_history.pop
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
__END__
|
108
|
+
|
109
|
+
To generate the Ruby classes `LinkState` and `LinkHistory` with their current features and specifications, including the custom `==` method for object comparison and the implementation to handle empty states, you can use the following prompt:
|
110
|
+
|
111
|
+
---
|
112
|
+
|
113
|
+
Create Ruby classes `LinkState` and `LinkHistory` with the following specifications:
|
114
|
+
|
115
|
+
1. **Class `LinkState`**:
|
116
|
+
- Attributes: `block_name`, `document_filename`, `inherited_lines`.
|
117
|
+
- Initialize with optional parameters for each attribute, defaulting to `nil`.
|
118
|
+
- Include a class method `empty` that creates an instance with all attributes set to `nil`.
|
119
|
+
- Implement a custom `==` method for comparing instances based on attribute values.
|
120
|
+
|
121
|
+
2. **Class `LinkHistory`**:
|
122
|
+
- Use an array to manage a stack of `LinkState` instances.
|
123
|
+
- Implement the following methods:
|
124
|
+
- `push`: Adds a `LinkState` instance to the top of the stack.
|
125
|
+
- `pop`: Removes and returns the most recent `LinkState` from the stack, or returns an empty `LinkState` if the stack is empty.
|
126
|
+
- `peek`: Returns the most recent `LinkState` without removing it from the stack, or an empty `LinkState` if the stack is empty.
|
127
|
+
|
128
|
+
3. **Testing**:
|
129
|
+
- Write Minitest test cases to validate each method in `LinkHistory`. Test scenarios should include pushing and popping `LinkState` instances, and handling an empty `LinkHistory`.
|
130
|
+
|
131
|
+
The goal is to create a robust and efficient implementation of these classes, ensuring proper handling of stack operations and object comparisons.
|
data/lib/markdown_exec.rb
CHANGED
@@ -41,8 +41,6 @@ tap_config envvar: MarkdownExec::TAP_DEBUG
|
|
41
41
|
$stderr.sync = true
|
42
42
|
$stdout.sync = true
|
43
43
|
|
44
|
-
MDE_HISTORY_ENV_NAME = 'MDE_MENU_HISTORY'
|
45
|
-
|
46
44
|
# custom error: file specified is missing
|
47
45
|
#
|
48
46
|
class FileMissingError < StandardError; end
|
@@ -172,26 +170,6 @@ module MarkdownExec
|
|
172
170
|
}
|
173
171
|
end
|
174
172
|
|
175
|
-
def clear_required_file
|
176
|
-
ENV['MDE_LINK_REQUIRED_FILE'] = ''
|
177
|
-
end
|
178
|
-
|
179
|
-
# # Deletes a required temporary file specified by an environment variable.
|
180
|
-
# # The function checks if the file exists before attempting to delete it.
|
181
|
-
# # Clears the environment variable after deletion.
|
182
|
-
# #
|
183
|
-
# def delete_required_temp_file
|
184
|
-
# temp_blocks_file_path = ENV.fetch('MDE_LINK_REQUIRED_FILE', nil)
|
185
|
-
|
186
|
-
# return if temp_blocks_file_path.nil? || temp_blocks_file_path.empty?
|
187
|
-
|
188
|
-
# FileUtils.rm_f(temp_blocks_file_path)
|
189
|
-
|
190
|
-
# clear_required_file
|
191
|
-
# rescue StandardError
|
192
|
-
# error_handler('delete_required_temp_file')
|
193
|
-
# end
|
194
|
-
|
195
173
|
public
|
196
174
|
|
197
175
|
## Determines the correct filename to use for searching files
|
@@ -368,6 +346,16 @@ module MarkdownExec
|
|
368
346
|
:menu_chrome_color)}"
|
369
347
|
searcher = DirectorySearcher.new(value, [@options[:path]])
|
370
348
|
|
349
|
+
@fout.fout 'In file contents'
|
350
|
+
hash = searcher.search_in_file_contents
|
351
|
+
hash.each.with_index do |(key, v2), i1|
|
352
|
+
@fout.fout format('- %3.d: %s', i1 + 1, key)
|
353
|
+
@fout.fout AnsiFormatter.new(options).format_and_highlight_array(
|
354
|
+
v2.map { |nl| format('=%4.d: %s', nl.index, nl.line) },
|
355
|
+
highlight: [value]
|
356
|
+
)
|
357
|
+
end
|
358
|
+
|
371
359
|
@fout.fout 'In directory names'
|
372
360
|
@fout.fout AnsiFormatter.new(options).format_and_highlight_array(
|
373
361
|
searcher.search_in_directory_names, highlight: [value]
|
@@ -378,15 +366,6 @@ module MarkdownExec
|
|
378
366
|
searcher.search_in_file_names, highlight: [value]
|
379
367
|
).join("\n")
|
380
368
|
|
381
|
-
@fout.fout 'In file contents'
|
382
|
-
hash = searcher.search_in_file_contents
|
383
|
-
hash.each.with_index do |(key, v2), i1|
|
384
|
-
@fout.fout format('- %3.d: %s', i1 + 1, key)
|
385
|
-
@fout.fout AnsiFormatter.new(options).format_and_highlight_array(
|
386
|
-
v2.map { |nl| format('=%4.d: %s', nl.index, nl.line) },
|
387
|
-
highlight: [value]
|
388
|
-
)
|
389
|
-
end
|
390
369
|
exit
|
391
370
|
}
|
392
371
|
when 'help'
|
@@ -545,10 +524,8 @@ module MarkdownExec
|
|
545
524
|
public
|
546
525
|
|
547
526
|
def run
|
548
|
-
clear_required_file
|
549
527
|
initialize_and_parse_cli_options
|
550
528
|
execute_block_with_error_handling
|
551
|
-
@options.delete_required_temp_file
|
552
529
|
rescue StandardError
|
553
530
|
error_handler('run')
|
554
531
|
end
|
data/lib/mdoc.rb
CHANGED
@@ -3,8 +3,8 @@
|
|
3
3
|
|
4
4
|
# encoding=utf-8
|
5
5
|
|
6
|
-
require_relative 'filter'
|
7
6
|
require_relative 'block_types'
|
7
|
+
require_relative 'filter'
|
8
8
|
|
9
9
|
module MarkdownExec
|
10
10
|
##
|
@@ -75,7 +75,6 @@ module MarkdownExec
|
|
75
75
|
raise "Named code block `#{name}` not found. (@#{__LINE__})"
|
76
76
|
end
|
77
77
|
|
78
|
-
# all_dependency_names = [name_block.oname] + recursively_required(name_block[:reqs])
|
79
78
|
dependencies = collect_dependencies(name_block[:oname])
|
80
79
|
all_dependency_names = collect_unique_names(dependencies).push(name_block[:oname]).uniq
|
81
80
|
unmet_dependencies = all_dependency_names.dup
|
@@ -91,10 +90,11 @@ module MarkdownExec
|
|
91
90
|
else
|
92
91
|
[]
|
93
92
|
end + [fcb]
|
94
|
-
end.flatten(1)
|
95
|
-
|
96
|
-
|
97
|
-
|
93
|
+
end.flatten(1)
|
94
|
+
|
95
|
+
{ all_dependency_names: all_dependency_names,
|
96
|
+
blocks: blocks,
|
97
|
+
dependencies: dependencies,
|
98
98
|
unmet_dependencies: unmet_dependencies }
|
99
99
|
end
|
100
100
|
|
@@ -103,26 +103,37 @@ module MarkdownExec
|
|
103
103
|
# @param name [String] The name of the code block to start the collection from.
|
104
104
|
# @return [Array<String>] An array of strings containing the collected code blocks.
|
105
105
|
#
|
106
|
-
def collect_recursively_required_code(name, label_body: true, label_format_above: nil,
|
106
|
+
def collect_recursively_required_code(name, label_body: true, label_format_above: nil,
|
107
|
+
label_format_below: nil, block_source:)
|
107
108
|
block_search = collect_recursively_required_blocks(name)
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
109
|
+
if block_search[:blocks]
|
110
|
+
blocks = collect_wrapped_blocks(block_search[:blocks])
|
111
|
+
block_search.merge(
|
112
|
+
{ block_names: blocks.map { |block| block[:oname] },
|
113
|
+
code: blocks.map do |fcb|
|
114
|
+
if fcb[:cann]
|
115
|
+
collect_block_code_cann(fcb)
|
116
|
+
elsif fcb[:stdout]
|
117
|
+
collect_block_code_stdout(fcb)
|
118
|
+
elsif [BlockType::LINK, BlockType::OPTS,
|
119
|
+
BlockType::VARS].include? fcb[:shell]
|
120
|
+
nil
|
121
|
+
elsif fcb[:shell] == BlockType::PORT
|
122
|
+
collect_block_code_shell(fcb)
|
123
|
+
elsif label_body
|
124
|
+
[label_format_above && format(label_format_above,
|
125
|
+
block_source.merge({ block_name: fcb[:oname] }))] +
|
126
|
+
fcb[:body] +
|
127
|
+
[label_format_below && format(label_format_below,
|
128
|
+
block_source.merge({ block_name: fcb[:oname] }))]
|
129
|
+
else # raw body
|
130
|
+
fcb[:body]
|
131
|
+
end
|
132
|
+
end.compact.flatten(1).compact }
|
133
|
+
)
|
134
|
+
else
|
135
|
+
block_search.merge({ block_names: [], code: [] })
|
136
|
+
end
|
126
137
|
end
|
127
138
|
|
128
139
|
def collect_unique_names(hash)
|
@@ -279,11 +290,10 @@ module MarkdownExec
|
|
279
290
|
return memo unless source
|
280
291
|
|
281
292
|
if (block = get_block_by_anyname(source)).nil? || block.keys.empty?
|
282
|
-
if true
|
283
|
-
|
284
|
-
|
285
|
-
|
286
|
-
end
|
293
|
+
return memo if true
|
294
|
+
|
295
|
+
raise "Named code block `#{source}` not found. (@#{__LINE__})"
|
296
|
+
|
287
297
|
end
|
288
298
|
|
289
299
|
return memo unless block[:reqs]
|
data/lib/menu.src.yml
CHANGED
@@ -96,6 +96,7 @@
|
|
96
96
|
:default: false
|
97
97
|
:description: Dump BlocksInFile (stage 1)
|
98
98
|
:env_var: MDE_DUMP_BLOCKS_IN_FILE
|
99
|
+
:long_name: dump-blocks-in-file
|
99
100
|
:opt_name: dump_blocks_in_file
|
100
101
|
:procname: val_as_bool
|
101
102
|
|
@@ -103,6 +104,7 @@
|
|
103
104
|
:default: false
|
104
105
|
:description: Dump MenuBlocks (stage 2)
|
105
106
|
:env_var: MDE_DUMP_MENU_BLOCKS
|
107
|
+
:long_name: dump-menu-blocks
|
106
108
|
:opt_name: dump_menu_blocks
|
107
109
|
:procname: val_as_bool
|
108
110
|
|
@@ -110,6 +112,7 @@
|
|
110
112
|
:default: false
|
111
113
|
:description: Dump selected block
|
112
114
|
:env_var: MDE_DUMP_SELECTED_BLOCK
|
115
|
+
:long_name: dump-selected-block
|
113
116
|
:opt_name: dump_selected_block
|
114
117
|
:procname: val_as_bool
|
115
118
|
|
@@ -846,13 +849,13 @@
|
|
846
849
|
:opt_name: shell
|
847
850
|
:procname: val_as_str
|
848
851
|
|
849
|
-
- :default: "# -^- +%{
|
852
|
+
- :default: "# -^- +%{block_name} -o- %{document_filename} -^-"
|
850
853
|
:description: shell_code_label_format_above
|
851
854
|
:env_var: MDE_SHELL_CODE_LABEL_FORMAT_ABOVE
|
852
855
|
:opt_name: shell_code_label_format_above
|
853
856
|
:procname: val_as_str
|
854
857
|
|
855
|
-
- :default: "# -v- +%{
|
858
|
+
- :default: "# -v- +%{block_name} -v-"
|
856
859
|
:description: shell_code_label_format_below
|
857
860
|
:env_var: MDE_SHELL_CODE_LABEL_FORMAT_BELOW
|
858
861
|
:opt_name: shell_code_label_format_below
|
data/lib/menu.yml
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
# MDE - Markdown Executor (1.8.
|
1
|
+
# MDE - Markdown Executor (1.8.4)
|
2
2
|
---
|
3
3
|
- :description: Show current configuration values
|
4
4
|
:procname: show_config
|
@@ -81,18 +81,21 @@
|
|
81
81
|
:default: false
|
82
82
|
:description: Dump BlocksInFile (stage 1)
|
83
83
|
:env_var: MDE_DUMP_BLOCKS_IN_FILE
|
84
|
+
:long_name: dump-blocks-in-file
|
84
85
|
:opt_name: dump_blocks_in_file
|
85
86
|
:procname: val_as_bool
|
86
87
|
- :arg_name: BOOL
|
87
88
|
:default: false
|
88
89
|
:description: Dump MenuBlocks (stage 2)
|
89
90
|
:env_var: MDE_DUMP_MENU_BLOCKS
|
91
|
+
:long_name: dump-menu-blocks
|
90
92
|
:opt_name: dump_menu_blocks
|
91
93
|
:procname: val_as_bool
|
92
94
|
- :arg_name: BOOL
|
93
95
|
:default: false
|
94
96
|
:description: Dump selected block
|
95
97
|
:env_var: MDE_DUMP_SELECTED_BLOCK
|
98
|
+
:long_name: dump-selected-block
|
96
99
|
:opt_name: dump_selected_block
|
97
100
|
:procname: val_as_bool
|
98
101
|
- :default: fg_rgbh_ff_00_7f
|
@@ -727,12 +730,12 @@
|
|
727
730
|
:env_var: MDE_SHELL
|
728
731
|
:opt_name: shell
|
729
732
|
:procname: val_as_str
|
730
|
-
- :default: "# -^- +%{
|
733
|
+
- :default: "# -^- +%{block_name} -o- %{document_filename} -^-"
|
731
734
|
:description: shell_code_label_format_above
|
732
735
|
:env_var: MDE_SHELL_CODE_LABEL_FORMAT_ABOVE
|
733
736
|
:opt_name: shell_code_label_format_above
|
734
737
|
:procname: val_as_str
|
735
|
-
- :default: "# -v- +%{
|
738
|
+
- :default: "# -v- +%{block_name} -v-"
|
736
739
|
:description: shell_code_label_format_below
|
737
740
|
:env_var: MDE_SHELL_CODE_LABEL_FORMAT_BELOW
|
738
741
|
:opt_name: shell_code_label_format_below
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: markdown_exec
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.8.
|
4
|
+
version: 1.8.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Fareed Stevenson
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-12-
|
11
|
+
date: 2023-12-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: clipboard
|
@@ -145,6 +145,7 @@ files:
|
|
145
145
|
- lib/fout.rb
|
146
146
|
- lib/hash.rb
|
147
147
|
- lib/hash_delegator.rb
|
148
|
+
- lib/link_history.rb
|
148
149
|
- lib/markdown_exec.rb
|
149
150
|
- lib/markdown_exec/version.rb
|
150
151
|
- lib/mdoc.rb
|