markdown_exec 1.8.2 → 1.8.5

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.
@@ -0,0 +1,134 @@
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_dependencies, :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_dependencies [?, nil] the dependecy hierarcy.
15
+ # @param inherited_lines [Array<String>, nil] the inherited lines of code.
16
+ def initialize(block_name: nil, document_filename: nil,
17
+ inherited_block_names: [], inherited_dependencies: nil, inherited_lines: nil)
18
+ @block_name = block_name
19
+ @document_filename = document_filename
20
+ @inherited_block_names = inherited_block_names
21
+ @inherited_dependencies = inherited_dependencies
22
+ @inherited_lines = inherited_lines
23
+ end
24
+
25
+ # Creates an empty LinkState instance.
26
+ # @return [LinkState] an instance with all attributes set to their default values.
27
+ def self.empty
28
+ new
29
+ end
30
+
31
+ # Custom equality method to compare LinkState objects.
32
+ # @param other [LinkState] the other LinkState object to compare with.
33
+ # @return [Boolean] true if the objects are equal, false otherwise.
34
+ def ==(other)
35
+ other.class == self.class &&
36
+ other.block_name == block_name &&
37
+ other.document_filename == document_filename &&
38
+ other.inherited_block_names == inherited_block_names &&
39
+ other.inherited_dependencies == inherited_dependencies &&
40
+ other.inherited_lines == inherited_lines
41
+ end
42
+ end
43
+
44
+ class LinkHistory
45
+ def initialize
46
+ @history = []
47
+ end
48
+
49
+ # Peeks at the most recent LinkState, returns an empty LinkState if stack is empty.
50
+ def peek
51
+ @history.last || LinkState.empty
52
+ end
53
+
54
+ # Pops the most recent LinkState off the stack, returns an empty LinkState if stack is empty.
55
+ def pop
56
+ @history.pop || LinkState.empty
57
+ end
58
+
59
+ def prior_state_exist?
60
+ peek.document_filename.present?
61
+ end
62
+
63
+ # Pushes a LinkState onto the stack.
64
+ def push(link_state)
65
+ @history.push(link_state)
66
+ end
67
+ end
68
+ end
69
+
70
+ if $PROGRAM_NAME == __FILE__
71
+ require 'bundler/setup'
72
+ Bundler.require(:default)
73
+
74
+ require 'minitest/autorun'
75
+ require 'mocha/minitest'
76
+
77
+ module MarkdownExec
78
+ class TestLinkHistory < Minitest::Test
79
+ def setup
80
+ @link_history = LinkHistory.new
81
+ @link_state1 = LinkState.new(block_name: 'block1', document_filename: 'document1.txt',
82
+ inherited_lines: ['code1.rb'])
83
+ @link_state2 = LinkState.new(block_name: 'block2', document_filename: 'document2.txt',
84
+ inherited_lines: ['code2.rb'])
85
+ end
86
+
87
+ def test_push
88
+ @link_history.push(@link_state1)
89
+ assert_equal @link_state1, @link_history.peek
90
+ end
91
+
92
+ def test_pop
93
+ @link_history.push(@link_state1)
94
+ @link_history.push(@link_state2)
95
+ assert_equal @link_state2, @link_history.pop
96
+ assert_equal @link_state1, @link_history.peek
97
+ end
98
+
99
+ def test_peek_empty
100
+ assert_equal LinkState.empty, @link_history.peek
101
+ end
102
+
103
+ def test_pop_empty
104
+ assert_equal LinkState.empty, @link_history.pop
105
+ end
106
+ end
107
+ end
108
+ end
109
+
110
+ __END__
111
+
112
+ 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:
113
+
114
+ ---
115
+
116
+ Create Ruby classes `LinkState` and `LinkHistory` with the following specifications:
117
+
118
+ 1. **Class `LinkState`**:
119
+ - Attributes: `block_name`, `document_filename`, `inherited_lines`.
120
+ - Initialize with optional parameters for each attribute, defaulting to `nil`.
121
+ - Include a class method `empty` that creates an instance with all attributes set to `nil`.
122
+ - Implement a custom `==` method for comparing instances based on attribute values.
123
+
124
+ 2. **Class `LinkHistory`**:
125
+ - Use an array to manage a stack of `LinkState` instances.
126
+ - Implement the following methods:
127
+ - `push`: Adds a `LinkState` instance to the top of the stack.
128
+ - `pop`: Removes and returns the most recent `LinkState` from the stack, or returns an empty `LinkState` if the stack is empty.
129
+ - `peek`: Returns the most recent `LinkState` without removing it from the stack, or an empty `LinkState` if the stack is empty.
130
+
131
+ 3. **Testing**:
132
+ - Write Minitest test cases to validate each method in `LinkHistory`. Test scenarios should include pushing and popping `LinkState` instances, and handling an empty `LinkHistory`.
133
+
134
+ The goal is to create a robust and efficient implementation of these classes, ensuring proper handling of stack operations and object comparisons.
@@ -7,5 +7,5 @@ module MarkdownExec
7
7
  BIN_NAME = 'mde'
8
8
  GEM_NAME = 'markdown_exec'
9
9
  TAP_DEBUG = 'MDE_DEBUG'
10
- VERSION = '1.8.2'
10
+ VERSION = '1.8.5'
11
11
  end
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
@@ -51,6 +49,11 @@ def dp(str)
51
49
  lout " => #{str}", level: DISPLAY_LEVEL_DEBUG
52
50
  end
53
51
 
52
+ def rbi
53
+ pp(caller.take(4).map.with_index { |line, ind| " - #{ind}: #{line}" })
54
+ binding.irb
55
+ end
56
+
54
57
  def rbp
55
58
  rpry
56
59
  pp(caller.take(4).map.with_index { |line, ind| " - #{ind}: #{line}" })
@@ -60,7 +63,7 @@ end
60
63
  def bpp(*args)
61
64
  pp '+ bpp()'
62
65
  pp(*args.map.with_index { |line, ind| " - #{ind}: #{line}" })
63
- rbp
66
+ rbi
64
67
  end
65
68
 
66
69
  def rpry
@@ -172,26 +175,6 @@ module MarkdownExec
172
175
  }
173
176
  end
174
177
 
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
178
  public
196
179
 
197
180
  ## Determines the correct filename to use for searching files
@@ -368,6 +351,16 @@ module MarkdownExec
368
351
  :menu_chrome_color)}"
369
352
  searcher = DirectorySearcher.new(value, [@options[:path]])
370
353
 
354
+ @fout.fout 'In file contents'
355
+ hash = searcher.search_in_file_contents
356
+ hash.each.with_index do |(key, v2), i1|
357
+ @fout.fout format('- %3.d: %s', i1 + 1, key)
358
+ @fout.fout AnsiFormatter.new(options).format_and_highlight_array(
359
+ v2.map { |nl| format('=%4.d: %s', nl.index, nl.line) },
360
+ highlight: [value]
361
+ )
362
+ end
363
+
371
364
  @fout.fout 'In directory names'
372
365
  @fout.fout AnsiFormatter.new(options).format_and_highlight_array(
373
366
  searcher.search_in_directory_names, highlight: [value]
@@ -378,15 +371,6 @@ module MarkdownExec
378
371
  searcher.search_in_file_names, highlight: [value]
379
372
  ).join("\n")
380
373
 
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
374
  exit
391
375
  }
392
376
  when 'help'
@@ -545,12 +529,12 @@ module MarkdownExec
545
529
  public
546
530
 
547
531
  def run
548
- clear_required_file
549
532
  initialize_and_parse_cli_options
550
533
  execute_block_with_error_handling
551
- @options.delete_required_temp_file
552
534
  rescue StandardError
553
535
  error_handler('run')
536
+ ensure
537
+ yield if block_given?
554
538
  end
555
539
 
556
540
  private
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) #.tap { rbp }
95
- { all_dependency_names: all_dependency_names,
96
- blocks: blocks,
97
- dependencies: dependencies,
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, label_format_below: 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
- block_search.merge({ code: collect_wrapped_blocks(block_search[:blocks]).map do |fcb|
109
- if fcb[:cann]
110
- collect_block_code_cann(fcb)
111
- elsif fcb[:stdout]
112
- collect_block_code_stdout(fcb)
113
- elsif [BlockType::LINK, BlockType::OPTS,
114
- BlockType::VARS].include? fcb[:shell]
115
- nil
116
- elsif fcb[:shell] == BlockType::PORT
117
- collect_block_code_shell(fcb)
118
- elsif label_body
119
- [label_format_above && format(label_format_above, { name: fcb[:oname] })] +
120
- fcb[:body] +
121
- [label_format_below && format(label_format_below, { name: fcb[:oname] })]
122
- else # raw body
123
- fcb[:body]
124
- end
125
- end.compact.flatten(1).compact })
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
- return memo
284
- else
285
- raise "Named code block `#{source}` not found. (@#{__LINE__})"
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
@@ -92,17 +92,35 @@
92
92
  :opt_name: document_load_opts_block_name
93
93
  :procname: val_as_str
94
94
 
95
+ - :arg_name: BOOL
96
+ :default: false
97
+ :description: Dump @delegate_object
98
+ :env_var: MDE_DUMP_DELEGATE_OBJECT
99
+ :long_name: dump-dump-delegate-object
100
+ :opt_name: dump_delegate_object
101
+ :procname: val_as_bool
102
+
95
103
  - :arg_name: BOOL
96
104
  :default: false
97
105
  :description: Dump BlocksInFile (stage 1)
98
106
  :env_var: MDE_DUMP_BLOCKS_IN_FILE
107
+ :long_name: dump-blocks-in-file
99
108
  :opt_name: dump_blocks_in_file
100
109
  :procname: val_as_bool
101
110
 
111
+ - :arg_name: BOOL
112
+ :default: false
113
+ :description: Dump inherited lines
114
+ :env_var: MDE_DUMP_INHERITED_LINES
115
+ :long_name: dump-dump-inherited-lines
116
+ :opt_name: dump_inherited_lines
117
+ :procname: val_as_bool
118
+
102
119
  - :arg_name: BOOL
103
120
  :default: false
104
121
  :description: Dump MenuBlocks (stage 2)
105
122
  :env_var: MDE_DUMP_MENU_BLOCKS
123
+ :long_name: dump-menu-blocks
106
124
  :opt_name: dump_menu_blocks
107
125
  :procname: val_as_bool
108
126
 
@@ -110,6 +128,7 @@
110
128
  :default: false
111
129
  :description: Dump selected block
112
130
  :env_var: MDE_DUMP_SELECTED_BLOCK
131
+ :long_name: dump-selected-block
113
132
  :opt_name: dump_selected_block
114
133
  :procname: val_as_bool
115
134
 
@@ -846,13 +865,13 @@
846
865
  :opt_name: shell
847
866
  :procname: val_as_str
848
867
 
849
- - :default: "# -^- +%{name} -^-"
868
+ - :default: "# -^- +%{block_name} -o- %{document_filename} -^-"
850
869
  :description: shell_code_label_format_above
851
870
  :env_var: MDE_SHELL_CODE_LABEL_FORMAT_ABOVE
852
871
  :opt_name: shell_code_label_format_above
853
872
  :procname: val_as_str
854
873
 
855
- - :default: "# -v- +%{name} -v-"
874
+ - :default: "# -v- +%{block_name} -v-"
856
875
  :description: shell_code_label_format_below
857
876
  :env_var: MDE_SHELL_CODE_LABEL_FORMAT_BELOW
858
877
  :opt_name: shell_code_label_format_below
data/lib/menu.yml CHANGED
@@ -1,4 +1,4 @@
1
- # MDE - Markdown Executor (1.8.2)
1
+ # MDE - Markdown Executor (1.8.5)
2
2
  ---
3
3
  - :description: Show current configuration values
4
4
  :procname: show_config
@@ -77,22 +77,39 @@
77
77
  :env_var: MDE_DOCUMENT_LOAD_OPTS_BLOCK_NAME
78
78
  :opt_name: document_load_opts_block_name
79
79
  :procname: val_as_str
80
+ - :arg_name: BOOL
81
+ :default: false
82
+ :description: Dump @delegate_object
83
+ :env_var: MDE_DUMP_DELEGATE_OBJECT
84
+ :long_name: dump-dump-delegate-object
85
+ :opt_name: dump_delegate_object
86
+ :procname: val_as_bool
80
87
  - :arg_name: BOOL
81
88
  :default: false
82
89
  :description: Dump BlocksInFile (stage 1)
83
90
  :env_var: MDE_DUMP_BLOCKS_IN_FILE
91
+ :long_name: dump-blocks-in-file
84
92
  :opt_name: dump_blocks_in_file
85
93
  :procname: val_as_bool
94
+ - :arg_name: BOOL
95
+ :default: false
96
+ :description: Dump inherited lines
97
+ :env_var: MDE_DUMP_INHERITED_LINES
98
+ :long_name: dump-dump-inherited-lines
99
+ :opt_name: dump_inherited_lines
100
+ :procname: val_as_bool
86
101
  - :arg_name: BOOL
87
102
  :default: false
88
103
  :description: Dump MenuBlocks (stage 2)
89
104
  :env_var: MDE_DUMP_MENU_BLOCKS
105
+ :long_name: dump-menu-blocks
90
106
  :opt_name: dump_menu_blocks
91
107
  :procname: val_as_bool
92
108
  - :arg_name: BOOL
93
109
  :default: false
94
110
  :description: Dump selected block
95
111
  :env_var: MDE_DUMP_SELECTED_BLOCK
112
+ :long_name: dump-selected-block
96
113
  :opt_name: dump_selected_block
97
114
  :procname: val_as_bool
98
115
  - :default: fg_rgbh_ff_00_7f
@@ -727,12 +744,12 @@
727
744
  :env_var: MDE_SHELL
728
745
  :opt_name: shell
729
746
  :procname: val_as_str
730
- - :default: "# -^- +%{name} -^-"
747
+ - :default: "# -^- +%{block_name} -o- %{document_filename} -^-"
731
748
  :description: shell_code_label_format_above
732
749
  :env_var: MDE_SHELL_CODE_LABEL_FORMAT_ABOVE
733
750
  :opt_name: shell_code_label_format_above
734
751
  :procname: val_as_str
735
- - :default: "# -v- +%{name} -v-"
752
+ - :default: "# -v- +%{block_name} -v-"
736
753
  :description: shell_code_label_format_below
737
754
  :env_var: MDE_SHELL_CODE_LABEL_FORMAT_BELOW
738
755
  :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.2
4
+ version: 1.8.5
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-12 00:00:00.000000000 Z
11
+ date: 2023-12-22 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: clipboard
@@ -119,6 +119,7 @@ files:
119
119
  - examples/import1.md
120
120
  - examples/include.md
121
121
  - examples/infile_config.md
122
+ - examples/linked.md
122
123
  - examples/linked1.md
123
124
  - examples/linked2.md
124
125
  - examples/linked3.md
@@ -145,6 +146,7 @@ files:
145
146
  - lib/fout.rb
146
147
  - lib/hash.rb
147
148
  - lib/hash_delegator.rb
149
+ - lib/link_history.rb
148
150
  - lib/markdown_exec.rb
149
151
  - lib/markdown_exec/version.rb
150
152
  - lib/mdoc.rb