Class: Rng::RncBuilder

Inherits:
Object
  • Object
show all
Defined in:
lib/rng/rnc_builder.rb

Overview

RncBuilder converts RNG Grammar objects to RNC (RELAX NG Compact Syntax) text format.

This class traverses the RNG object model and generates readable RNC syntax strings. It handles all major RELAX NG patterns including:

  • Elements and attributes

  • Named pattern definitions

  • Occurrence markers (*, +, ?)

  • Choice and group patterns

  • Mixed content

  • Value literals and datatypes

  • Namespace declarations

Examples:

Convert a Grammar object to RNC

grammar = Rng::Grammar.new
# ... populate grammar ...
builder = Rng::RncBuilder.new
rnc_text = builder.build(grammar)

Instance Method Summary collapse

Instance Method Details

#build(schema) ⇒ String

Build RNC text from a Grammar object or Element

Parameters:

Returns:

  • (String)

    RNC text representation



26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
# File 'lib/rng/rnc_builder.rb', line 26

def build(schema)
  @datatype_prefix = nil
  @datatype_library_uri = nil
  # Handle simple element (direct Element object, not Grammar)
  return build_element(schema) if schema.is_a?(Element)

  # Grammar with start and/or named patterns
  result = []

  # Collect datatype libraries from data elements
  collect_datatype_libraries(schema)

  # Add namespace declaration if present
  if schema.ns && !schema.ns.empty? && schema.ns != 'omitted' && schema.ns != 'empty'
    result << "default namespace = \"#{schema.ns}\""
    result << ''
  end

  # Add datatype library if present (grammar-level or from data elements)
  dt_lib = schema.datatypeLibrary if schema.datatypeLibrary &&
                                     !%w[omitted empty].include?(schema.datatypeLibrary)
  dt_lib ||= @datatype_library_uri
  if dt_lib
    result << "datatypes xsd = \"#{dt_lib}\""
    @datatype_prefix = 'xsd'
    result << ''
  end

  # Process start pattern
  if schema.start && !schema.start.empty?
    start = schema.start.first
    # Add documentation if present
    result << build_documentation(start.documentation).chomp if start.documentation && !start.documentation.empty?
    start_pattern = build_pattern(start)
    result << "start = #{start_pattern}"
    result << ''
  end

  # Process named patterns (define elements)
  if schema.define && !schema.define.empty?
    schema.define.each do |define|
      # Add documentation if present
      result << build_documentation(define.documentation).chomp if define.documentation && !define.documentation.empty?
      pattern = build_pattern(define)
      result << "#{define.name} = #{pattern}"
      result << ''
    end
  end

  # Process div elements (grouping containers)
  if schema.div && !schema.div.empty?
    schema.div.each do |div|
      div_content = build_div(div)
      result << div_content
      result << ''
    end
  end

  result.join("\n")
end

#build_div(div) ⇒ String

Build RNC syntax for a div grouping construct

Parameters:

Returns:

  • (String)

    RNC div syntax



105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
# File 'lib/rng/rnc_builder.rb', line 105

def build_div(div)
  result = 'div {'
  parts = []

  # Process divs within div
  if div.div && !div.div.empty?
    div.div.each do |nested_div|
      parts << build_div(nested_div)
    end
  end

  # Process start within div
  if div.start && !div.start.empty?
    div.start.each do |start|
      parts << "start = #{build_pattern(start)}"
    end
  end

  # Process defines within div
  if div.define && !div.define.empty?
    div.define.each do |define|
      parts << "#{define.name} = #{build_pattern(define)}"
    end
  end

  if parts.empty?
    "#{result} }"
  else
    "#{result}\n  #{parts.join("\n  ")}\n}"
  end
end

#escape_rnc_string(str) ⇒ String

Escape a string value for use in RNC double-quoted string literals. RNC string escape sequences: \ (backslash), " (double quote), n (newline), r (carriage return), t (tab)

Parameters:

  • str (String)

    The string to escape

Returns:

  • (String)

    The escaped string



93
94
95
96
97
98
99
# File 'lib/rng/rnc_builder.rb', line 93

def escape_rnc_string(str)
  str.gsub('\\') { '\\\\' }
     .gsub('"') { '\\"' }
     .gsub("\n") { '\\n' }
     .gsub("\r") { '\\r' }
     .gsub("\t") { '\\t' }
end