Class: Markbridge::Parsers::BBCode::ParserState

Inherits:
Object
  • Object
show all
Defined in:
lib/markbridge/parsers/bbcode/parser_state.rb

Overview

Manages parsing state

Constant Summary collapse

MAX_DEPTH =
100

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(root) ⇒ ParserState

Returns a new instance of ParserState.



12
13
14
15
16
17
18
19
20
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 12

def initialize(root)
  @root = root
  @current = root
  @depth = 0
  @node_stack = [root]
  @auto_closed_count = 0
  @depth_exceeded_count = 0
  @unclosed_raw_tags = Hash.new(0)
end

Instance Attribute Details

#auto_closed_countObject (readonly)

Returns the value of attribute auto_closed_count.



10
11
12
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 10

def auto_closed_count
  @auto_closed_count
end

#currentObject (readonly)

Returns the value of attribute current.



10
11
12
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 10

def current
  @current
end

#depthObject (readonly)

Returns the value of attribute depth.



10
11
12
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 10

def depth
  @depth
end

#depth_exceeded_countObject (readonly)

Returns the value of attribute depth_exceeded_count.



10
11
12
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 10

def depth_exceeded_count
  @depth_exceeded_count
end

#unclosed_raw_tagsObject (readonly)

Returns the value of attribute unclosed_raw_tags.



10
11
12
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 10

def unclosed_raw_tags
  @unclosed_raw_tags
end

Instance Method Details

#add_child(node) ⇒ Object

Add a child to current node without changing context

Parameters:



60
61
62
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 60

def add_child(node)
  @current << node
end

#auto_close!(count = 1) ⇒ Object

Increment the count of auto-closed tags after external reconciliation

Parameters:

  • count (Integer) (defaults to: 1)


66
67
68
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 66

def auto_close!(count = 1)
  @auto_closed_count += count
end

#elements_from_current(limit = nil) ⇒ Array<AST::Node>

Return elements from the current node downward

Parameters:

  • limit (Integer, nil) (defaults to: nil)

    number of elements to include from the top

Returns:



79
80
81
82
83
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 79

def elements_from_current(limit = nil)
  max_offset = @node_stack.size - 1
  limit = [limit || max_offset, max_offset].min
  (0..limit).map { |offset| @node_stack.fetch(max_offset - offset) }
end

#mark_unclosed_raw!(tag_name) ⇒ Object

Mark a raw tag as unclosed (for tracking parsing issues)

Parameters:

  • tag_name (String)


72
73
74
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 72

def mark_unclosed_raw!(tag_name)
  @unclosed_raw_tags[tag_name] += 1
end

#popAST::Element

Pop current element and return to parent

Returns:



49
50
51
52
53
54
55
56
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 49

def pop
  return @root if @node_stack.size == 1

  @node_stack.pop
  @current = @node_stack.fetch(-1)
  @depth -= 1
  @current
end

#push(element, token: nil) ⇒ Boolean

Add element as child to current node and push the element onto the stack Uses graceful degradation: if max depth is exceeded and token is provided, treats the tag as text instead of raising. If no token is provided, raises MaxDepthExceededError (for backwards compatibility).

Parameters:

  • element (AST::Element)
  • token (Token, nil) (defaults to: nil)

    the token that created this element (for graceful degradation)

Returns:

  • (Boolean)

    true if pushed successfully, false if depth exceeded

Raises:



30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/markbridge/parsers/bbcode/parser_state.rb', line 30

def push(element, token: nil)
  if @depth == MAX_DEPTH
    raise MaxDepthExceededError, MAX_DEPTH unless token

    # Graceful degradation: treat as text
    @current << AST::Text.new(token.source)
    @depth_exceeded_count += 1
    return false
  end

  @current << element
  @current = element
  @node_stack << element
  @depth += 1
  true
end