wlang 0.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.
- data/LICENCE.rdoc +25 -0
 - data/README.rdoc +111 -0
 - data/bin/wlang +24 -0
 - data/doc/specification/about.rdoc +61 -0
 - data/doc/specification/dialects.wtpl +0 -0
 - data/doc/specification/examples.rb +3 -0
 - data/doc/specification/glossary.wtpl +14 -0
 - data/doc/specification/hosting.rdoc +0 -0
 - data/doc/specification/overview.rdoc +116 -0
 - data/doc/specification/rulesets.wtpl +87 -0
 - data/doc/specification/specification.css +52 -0
 - data/doc/specification/specification.html +1361 -0
 - data/doc/specification/specification.js +8 -0
 - data/doc/specification/specification.wtpl +41 -0
 - data/doc/specification/specification.yml +430 -0
 - data/doc/specification/symbols.wtpl +16 -0
 - data/lib/wlang.rb +186 -0
 - data/lib/wlang/basic_object.rb +19 -0
 - data/lib/wlang/dialect.rb +230 -0
 - data/lib/wlang/dialect_dsl.rb +136 -0
 - data/lib/wlang/dialect_loader.rb +69 -0
 - data/lib/wlang/dialects/coderay_dialect.rb +35 -0
 - data/lib/wlang/dialects/plain_text_dialect.rb +75 -0
 - data/lib/wlang/dialects/rdoc_dialect.rb +33 -0
 - data/lib/wlang/dialects/ruby_dialect.rb +35 -0
 - data/lib/wlang/dialects/sql_dialect.rb +38 -0
 - data/lib/wlang/dialects/standard_dialects.rb +113 -0
 - data/lib/wlang/dialects/xhtml_dialect.rb +40 -0
 - data/lib/wlang/encoder.rb +66 -0
 - data/lib/wlang/encoder_set.rb +117 -0
 - data/lib/wlang/errors.rb +37 -0
 - data/lib/wlang/intelligent_buffer.rb +94 -0
 - data/lib/wlang/parser.rb +251 -0
 - data/lib/wlang/parser_context.rb +146 -0
 - data/lib/wlang/ruby_extensions.rb +21 -0
 - data/lib/wlang/rule.rb +66 -0
 - data/lib/wlang/rule_set.rb +93 -0
 - data/lib/wlang/rulesets/basic_ruleset.rb +75 -0
 - data/lib/wlang/rulesets/buffering_ruleset.rb +103 -0
 - data/lib/wlang/rulesets/context_ruleset.rb +115 -0
 - data/lib/wlang/rulesets/encoding_ruleset.rb +73 -0
 - data/lib/wlang/rulesets/imperative_ruleset.rb +132 -0
 - data/lib/wlang/rulesets/ruleset_utils.rb +296 -0
 - data/lib/wlang/template.rb +79 -0
 - data/lib/wlang/wlang_command.rb +54 -0
 - data/lib/wlang/wlang_command_options.rb +158 -0
 - data/test/sandbox.rb +1 -0
 - data/test/test_all.rb +8 -0
 - data/test/wlang/anagram_bugs_test.rb +111 -0
 - data/test/wlang/basic_ruleset_test.rb +52 -0
 - data/test/wlang/buffering_ruleset_test.rb +102 -0
 - data/test/wlang/buffering_template1.wtpl +1 -0
 - data/test/wlang/buffering_template2.wtpl +1 -0
 - data/test/wlang/buffering_template3.wtpl +1 -0
 - data/test/wlang/buffering_template4.wtpl +1 -0
 - data/test/wlang/buffering_template5.wtpl +1 -0
 - data/test/wlang/context_ruleset_test.rb +32 -0
 - data/test/wlang/data.rb +3 -0
 - data/test/wlang/encoder_set_test.rb +42 -0
 - data/test/wlang/imperative_ruleset_test.rb +107 -0
 - data/test/wlang/intelligent_buffer_test.rb +194 -0
 - data/test/wlang/othersymbols_test.rb +16 -0
 - data/test/wlang/parser_context_test.rb +29 -0
 - data/test/wlang/parser_test.rb +89 -0
 - data/test/wlang/plain_text_dialect_test.rb +21 -0
 - data/test/wlang/ruby_dialect_test.rb +100 -0
 - data/test/wlang/ruby_expected.rb +3 -0
 - data/test/wlang/ruby_template.wrb +3 -0
 - data/test/wlang/ruleset_utils_test.rb +245 -0
 - data/test/wlang/specification_examples_test.rb +52 -0
 - data/test/wlang/test_utils.rb +25 -0
 - data/test/wlang/wlang_test.rb +80 -0
 - metadata +136 -0
 
| 
         @@ -0,0 +1,79 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            module WLang
         
     | 
| 
      
 2 
     | 
    
         
            +
              
         
     | 
| 
      
 3 
     | 
    
         
            +
              # 
         
     | 
| 
      
 4 
     | 
    
         
            +
              # Template in a given wlang dialect, providing a default context object.
         
     | 
| 
      
 5 
     | 
    
         
            +
              #
         
     | 
| 
      
 6 
     | 
    
         
            +
              class Template
         
     | 
| 
      
 7 
     | 
    
         
            +
              
         
     | 
| 
      
 8 
     | 
    
         
            +
                # Recognized symbols for blocks
         
     | 
| 
      
 9 
     | 
    
         
            +
                BLOCK_SYMBOLS = {:braces   => ['{', '}'],
         
     | 
| 
      
 10 
     | 
    
         
            +
                                 :brackets => ['[', ']'],
         
     | 
| 
      
 11 
     | 
    
         
            +
                                 :parentheses => ['(', ')']}
         
     | 
| 
      
 12 
     | 
    
         
            +
              
         
     | 
| 
      
 13 
     | 
    
         
            +
                # Template wlang dialect (wlang/...)
         
     | 
| 
      
 14 
     | 
    
         
            +
                attr_reader :dialect
         
     | 
| 
      
 15 
     | 
    
         
            +
             
     | 
| 
      
 16 
     | 
    
         
            +
                # Instantiation context
         
     | 
| 
      
 17 
     | 
    
         
            +
                attr_reader :context
         
     | 
| 
      
 18 
     | 
    
         
            +
                
         
     | 
| 
      
 19 
     | 
    
         
            +
                # Block symbols
         
     | 
| 
      
 20 
     | 
    
         
            +
                attr_reader :block_symbols
         
     | 
| 
      
 21 
     | 
    
         
            +
              
         
     | 
| 
      
 22 
     | 
    
         
            +
                # Attached file source
         
     | 
| 
      
 23 
     | 
    
         
            +
                attr_accessor :source_file
         
     | 
| 
      
 24 
     | 
    
         
            +
              
         
     | 
| 
      
 25 
     | 
    
         
            +
                #
         
     | 
| 
      
 26 
     | 
    
         
            +
                # Creates a template instance.
         
     | 
| 
      
 27 
     | 
    
         
            +
                #
         
     | 
| 
      
 28 
     | 
    
         
            +
                def initialize(source, dialect, context=nil, block_symbols = :braces)
         
     | 
| 
      
 29 
     | 
    
         
            +
                  raise(ArgumentError, "Source is mandatory") if source.nil?
         
     | 
| 
      
 30 
     | 
    
         
            +
                  if String===dialect
         
     | 
| 
      
 31 
     | 
    
         
            +
                    dname, dialect = dialect, WLang::dialect(dialect)
         
     | 
| 
      
 32 
     | 
    
         
            +
                    raise(ArgumentError, "Unknown dialect #{dname}") if dialect.nil?
         
     | 
| 
      
 33 
     | 
    
         
            +
                  end     
         
     | 
| 
      
 34 
     | 
    
         
            +
                  raise(ArgumentError, "Dialect is mandatory") unless WLang::Dialect===dialect
         
     | 
| 
      
 35 
     | 
    
         
            +
                  @source = source
         
     | 
| 
      
 36 
     | 
    
         
            +
                  @dialect = dialect
         
     | 
| 
      
 37 
     | 
    
         
            +
                  @context = WLang::Parser::Context.new(context)  
         
     | 
| 
      
 38 
     | 
    
         
            +
                  @block_symbols = block_symbols
         
     | 
| 
      
 39 
     | 
    
         
            +
                end
         
     | 
| 
      
 40 
     | 
    
         
            +
              
         
     | 
| 
      
 41 
     | 
    
         
            +
                # Resolved a relative uri
         
     | 
| 
      
 42 
     | 
    
         
            +
                def file_resolve(uri, exists=false)
         
     | 
| 
      
 43 
     | 
    
         
            +
                  raise("Unable to resolve #{uri}, this template is not attached to a file")\
         
     | 
| 
      
 44 
     | 
    
         
            +
                    unless @source_file
         
     | 
| 
      
 45 
     | 
    
         
            +
                  target = File.join(File.dirname(@source_file), uri)
         
     | 
| 
      
 46 
     | 
    
         
            +
                  if exists and not(File.exists?(target))
         
     | 
| 
      
 47 
     | 
    
         
            +
                    raise "File '#{uri}' does not exists"
         
     | 
| 
      
 48 
     | 
    
         
            +
                  end
         
     | 
| 
      
 49 
     | 
    
         
            +
                  target
         
     | 
| 
      
 50 
     | 
    
         
            +
                end
         
     | 
| 
      
 51 
     | 
    
         
            +
              
         
     | 
| 
      
 52 
     | 
    
         
            +
                # Returns template's source text
         
     | 
| 
      
 53 
     | 
    
         
            +
                def source_text
         
     | 
| 
      
 54 
     | 
    
         
            +
                  case @source
         
     | 
| 
      
 55 
     | 
    
         
            +
                  when String
         
     | 
| 
      
 56 
     | 
    
         
            +
                    @source
         
     | 
| 
      
 57 
     | 
    
         
            +
                  else
         
     | 
| 
      
 58 
     | 
    
         
            +
                    @source.to_s
         
     | 
| 
      
 59 
     | 
    
         
            +
                  end
         
     | 
| 
      
 60 
     | 
    
         
            +
                end
         
     | 
| 
      
 61 
     | 
    
         
            +
              
         
     | 
| 
      
 62 
     | 
    
         
            +
                #
         
     | 
| 
      
 63 
     | 
    
         
            +
                # Instantiate the template, with an additional context and an output buffer.
         
     | 
| 
      
 64 
     | 
    
         
            +
                #
         
     | 
| 
      
 65 
     | 
    
         
            +
                def instantiate(buffer=nil, context=nil)
         
     | 
| 
      
 66 
     | 
    
         
            +
                  unless context.nil? 
         
     | 
| 
      
 67 
     | 
    
         
            +
                    @context.push(context)
         
     | 
| 
      
 68 
     | 
    
         
            +
                  end
         
     | 
| 
      
 69 
     | 
    
         
            +
                  parser = WLang::Parser.instantiator(self, buffer)
         
     | 
| 
      
 70 
     | 
    
         
            +
                  instantiated = parser.instantiate
         
     | 
| 
      
 71 
     | 
    
         
            +
                  unless context.nil?
         
     | 
| 
      
 72 
     | 
    
         
            +
                    @context.pop
         
     | 
| 
      
 73 
     | 
    
         
            +
                  end
         
     | 
| 
      
 74 
     | 
    
         
            +
                  instantiated[0]
         
     | 
| 
      
 75 
     | 
    
         
            +
                end
         
     | 
| 
      
 76 
     | 
    
         
            +
              
         
     | 
| 
      
 77 
     | 
    
         
            +
              end # class Template
         
     | 
| 
      
 78 
     | 
    
         
            +
              
         
     | 
| 
      
 79 
     | 
    
         
            +
            end # module WLang
         
     | 
| 
         @@ -0,0 +1,54 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'wlang'
         
     | 
| 
      
 2 
     | 
    
         
            +
            require 'wlang/wlang_command_options'
         
     | 
| 
      
 3 
     | 
    
         
            +
            require 'wlang/dialects/standard_dialects'
         
     | 
| 
      
 4 
     | 
    
         
            +
            module WLang
         
     | 
| 
      
 5 
     | 
    
         
            +
              
         
     | 
| 
      
 6 
     | 
    
         
            +
              #
         
     | 
| 
      
 7 
     | 
    
         
            +
              # Provides the _wlang_ commandline tool. See 'wlang --help' for documentation.
         
     | 
| 
      
 8 
     | 
    
         
            +
              #
         
     | 
| 
      
 9 
     | 
    
         
            +
              class WLangCommand
         
     | 
| 
      
 10 
     | 
    
         
            +
              
         
     | 
| 
      
 11 
     | 
    
         
            +
                # Creates a commandline instance.
         
     | 
| 
      
 12 
     | 
    
         
            +
                def initialize()
         
     | 
| 
      
 13 
     | 
    
         
            +
                end
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
                # Run _wlang_ commandline on specific arguments 
         
     | 
| 
      
 16 
     | 
    
         
            +
                def run(args)
         
     | 
| 
      
 17 
     | 
    
         
            +
                  # parse the options
         
     | 
| 
      
 18 
     | 
    
         
            +
                  options = Options.new.parse(args)
         
     | 
| 
      
 19 
     | 
    
         
            +
                
         
     | 
| 
      
 20 
     | 
    
         
            +
                  # get output buffer
         
     | 
| 
      
 21 
     | 
    
         
            +
                  buffer = STDOUT
         
     | 
| 
      
 22 
     | 
    
         
            +
                  if options.output_file
         
     | 
| 
      
 23 
     | 
    
         
            +
                    buffer = File.new(options.output_file, "w")
         
     | 
| 
      
 24 
     | 
    
         
            +
                  end
         
     | 
| 
      
 25 
     | 
    
         
            +
                
         
     | 
| 
      
 26 
     | 
    
         
            +
                  source = File.read(options.template_file)
         
     | 
| 
      
 27 
     | 
    
         
            +
                  dialect = options.template_dialect
         
     | 
| 
      
 28 
     | 
    
         
            +
                  braces = options.template_brace
         
     | 
| 
      
 29 
     | 
    
         
            +
                  context = options.context_object
         
     | 
| 
      
 30 
     | 
    
         
            +
                  unless options.context_name.nil?
         
     | 
| 
      
 31 
     | 
    
         
            +
                    context = {options.context_name => context}
         
     | 
| 
      
 32 
     | 
    
         
            +
                  end
         
     | 
| 
      
 33 
     | 
    
         
            +
                  template = WLang::Template.new(source, dialect, context, braces)
         
     | 
| 
      
 34 
     | 
    
         
            +
                  template.source_file = options.template_file
         
     | 
| 
      
 35 
     | 
    
         
            +
                
         
     | 
| 
      
 36 
     | 
    
         
            +
                  if options.verbosity>1
         
     | 
| 
      
 37 
     | 
    
         
            +
                    puts "Instantiating #{options.template_file}"
         
     | 
| 
      
 38 
     | 
    
         
            +
                    puts "Using dialect #{dialect} : #{dialect.class}"
         
     | 
| 
      
 39 
     | 
    
         
            +
                    puts "Block delimiters are " << Template::BLOCK_SYMBOLS[braces].inspect
         
     | 
| 
      
 40 
     | 
    
         
            +
                    puts "Context is " << context.inspect
         
     | 
| 
      
 41 
     | 
    
         
            +
                  end
         
     | 
| 
      
 42 
     | 
    
         
            +
                
         
     | 
| 
      
 43 
     | 
    
         
            +
                  buffer << template.instantiate
         
     | 
| 
      
 44 
     | 
    
         
            +
                
         
     | 
| 
      
 45 
     | 
    
         
            +
                  # Flush and close if needed
         
     | 
| 
      
 46 
     | 
    
         
            +
                  if File===buffer
         
     | 
| 
      
 47 
     | 
    
         
            +
                    buffer.flush
         
     | 
| 
      
 48 
     | 
    
         
            +
                    buffer.close
         
     | 
| 
      
 49 
     | 
    
         
            +
                  end
         
     | 
| 
      
 50 
     | 
    
         
            +
                end
         
     | 
| 
      
 51 
     | 
    
         
            +
                
         
     | 
| 
      
 52 
     | 
    
         
            +
              end # class WLang
         
     | 
| 
      
 53 
     | 
    
         
            +
              
         
     | 
| 
      
 54 
     | 
    
         
            +
            end # module WLang
         
     | 
| 
         @@ -0,0 +1,158 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'optparse'
         
     | 
| 
      
 2 
     | 
    
         
            +
            module WLang
         
     | 
| 
      
 3 
     | 
    
         
            +
              class WLangCommand
         
     | 
| 
      
 4 
     | 
    
         
            +
              
         
     | 
| 
      
 5 
     | 
    
         
            +
                #
         
     | 
| 
      
 6 
     | 
    
         
            +
                # Options of the _wlang_ commandline
         
     | 
| 
      
 7 
     | 
    
         
            +
                #  
         
     | 
| 
      
 8 
     | 
    
         
            +
                class Options
         
     | 
| 
      
 9 
     | 
    
         
            +
             
     | 
| 
      
 10 
     | 
    
         
            +
                  # Source template file
         
     | 
| 
      
 11 
     | 
    
         
            +
                  attr_reader :template_file
         
     | 
| 
      
 12 
     | 
    
         
            +
              
         
     | 
| 
      
 13 
     | 
    
         
            +
                  # Template dialect
         
     | 
| 
      
 14 
     | 
    
         
            +
                  attr_reader :template_dialect
         
     | 
| 
      
 15 
     | 
    
         
            +
                  
         
     | 
| 
      
 16 
     | 
    
         
            +
                  # Which brace kind used in template (:braces, :brackes, :parentheses)
         
     | 
| 
      
 17 
     | 
    
         
            +
                  attr_reader :template_brace
         
     | 
| 
      
 18 
     | 
    
         
            +
              
         
     | 
| 
      
 19 
     | 
    
         
            +
                  # Context file
         
     | 
| 
      
 20 
     | 
    
         
            +
                  attr_reader :context_file
         
     | 
| 
      
 21 
     | 
    
         
            +
             
     | 
| 
      
 22 
     | 
    
         
            +
                  # Context object
         
     | 
| 
      
 23 
     | 
    
         
            +
                  attr_reader :context_object
         
     | 
| 
      
 24 
     | 
    
         
            +
              
         
     | 
| 
      
 25 
     | 
    
         
            +
                  # Context kind [:yaml, :ruby, :dsl]  
         
     | 
| 
      
 26 
     | 
    
         
            +
                  attr_reader :context_kind
         
     | 
| 
      
 27 
     | 
    
         
            +
             
     | 
| 
      
 28 
     | 
    
         
            +
                  # Name of the context
         
     | 
| 
      
 29 
     | 
    
         
            +
                  attr_reader :context_name
         
     | 
| 
      
 30 
     | 
    
         
            +
                
         
     | 
| 
      
 31 
     | 
    
         
            +
                  # Output file
         
     | 
| 
      
 32 
     | 
    
         
            +
                  attr_reader :output_file
         
     | 
| 
      
 33 
     | 
    
         
            +
             
     | 
| 
      
 34 
     | 
    
         
            +
                  # Verbose mode?
         
     | 
| 
      
 35 
     | 
    
         
            +
                  attr_reader :verbosity
         
     | 
| 
      
 36 
     | 
    
         
            +
              
         
     | 
| 
      
 37 
     | 
    
         
            +
                  # Initializes the options with default values
         
     | 
| 
      
 38 
     | 
    
         
            +
                  def initialize
         
     | 
| 
      
 39 
     | 
    
         
            +
                    @verbosity = 0
         
     | 
| 
      
 40 
     | 
    
         
            +
                    @template_brace = :braces
         
     | 
| 
      
 41 
     | 
    
         
            +
                  end
         
     | 
| 
      
 42 
     | 
    
         
            +
              
         
     | 
| 
      
 43 
     | 
    
         
            +
                  #
         
     | 
| 
      
 44 
     | 
    
         
            +
                  # Parses commandline options provided as an array of Strings.
         
     | 
| 
      
 45 
     | 
    
         
            +
                  #
         
     | 
| 
      
 46 
     | 
    
         
            +
                  def parse(argv)
         
     | 
| 
      
 47 
     | 
    
         
            +
                    opts = OptionParser.new do |opt|
         
     | 
| 
      
 48 
     | 
    
         
            +
                      opt.program_name = File.basename $0
         
     | 
| 
      
 49 
     | 
    
         
            +
                      opt.version = WLang::VERSION
         
     | 
| 
      
 50 
     | 
    
         
            +
                      opt.release = nil
         
     | 
| 
      
 51 
     | 
    
         
            +
                      opt.summary_indent = ' ' * 4
         
     | 
| 
      
 52 
     | 
    
         
            +
                      banner = <<-EOF
         
     | 
| 
      
 53 
     | 
    
         
            +
                        # Usage #{opt.program_name} [options] template context-file
         
     | 
| 
      
 54 
     | 
    
         
            +
                    
         
     | 
| 
      
 55 
     | 
    
         
            +
                        # Template is parsed as a wlang dialect (based on its extension by default) and 
         
     | 
| 
      
 56 
     | 
    
         
            +
                        # instantiated through a given context file.
         
     | 
| 
      
 57 
     | 
    
         
            +
                      EOF
         
     | 
| 
      
 58 
     | 
    
         
            +
                      opt.banner = banner.gsub(/[ \t]+# /, "")
         
     | 
| 
      
 59 
     | 
    
         
            +
                  
         
     | 
| 
      
 60 
     | 
    
         
            +
                      opt.separator nil
         
     | 
| 
      
 61 
     | 
    
         
            +
                      opt.separator "Options:"
         
     | 
| 
      
 62 
     | 
    
         
            +
                  
         
     | 
| 
      
 63 
     | 
    
         
            +
                      opt.on("-d", "--dialect=DIALECT", 
         
     | 
| 
      
 64 
     | 
    
         
            +
                             "Interpret source template as a given wlang dialect") do |value|
         
     | 
| 
      
 65 
     | 
    
         
            +
                        @template_dialect = value
         
     | 
| 
      
 66 
     | 
    
         
            +
                      end
         
     | 
| 
      
 67 
     | 
    
         
            +
                  
         
     | 
| 
      
 68 
     | 
    
         
            +
                      opt.on("-o", "--output=OUTPUT",
         
     | 
| 
      
 69 
     | 
    
         
            +
                             "Flush instantiation result in output file") do |value|
         
     | 
| 
      
 70 
     | 
    
         
            +
                        @output_file = value         
         
     | 
| 
      
 71 
     | 
    
         
            +
                      end
         
     | 
| 
      
 72 
     | 
    
         
            +
                  
         
     | 
| 
      
 73 
     | 
    
         
            +
                      opt.on("--brace=BRACE", ["brace", "parenthesis", "bracket"],
         
     | 
| 
      
 74 
     | 
    
         
            +
                             "Block delimiters used by the template file (braces, brackets, parentheses)") do |value|
         
     | 
| 
      
 75 
     | 
    
         
            +
                         # handle template brace
         
     | 
| 
      
 76 
     | 
    
         
            +
                         case value
         
     | 
| 
      
 77 
     | 
    
         
            +
                           when "brace", "braces", "{"
         
     | 
| 
      
 78 
     | 
    
         
            +
                             @template_brace = :braces
         
     | 
| 
      
 79 
     | 
    
         
            +
                           when "brackets", "bracket", "["
         
     | 
| 
      
 80 
     | 
    
         
            +
                             @template_brace = :brackets
         
     | 
| 
      
 81 
     | 
    
         
            +
                           when "parentheses", "parenthesis", "("
         
     | 
| 
      
 82 
     | 
    
         
            +
                             @template_brace = :parentheses
         
     | 
| 
      
 83 
     | 
    
         
            +
                           else
         
     | 
| 
      
 84 
     | 
    
         
            +
                             raise "Unknown brace kind #{brace}"
         
     | 
| 
      
 85 
     | 
    
         
            +
                         end
         
     | 
| 
      
 86 
     | 
    
         
            +
                      end
         
     | 
| 
      
 87 
     | 
    
         
            +
                  
         
     | 
| 
      
 88 
     | 
    
         
            +
                      opt.on("--context-name=NAME",
         
     | 
| 
      
 89 
     | 
    
         
            +
                             "Name of the context object") do |value|
         
     | 
| 
      
 90 
     | 
    
         
            +
                        @context_name = value         
         
     | 
| 
      
 91 
     | 
    
         
            +
                      end
         
     | 
| 
      
 92 
     | 
    
         
            +
                  
         
     | 
| 
      
 93 
     | 
    
         
            +
                      opt.on("--context-kind=KIND", ["yaml", "ruby", "dsl"],
         
     | 
| 
      
 94 
     | 
    
         
            +
                             "Kind of context object (yaml, ruby, dsl)") do |value|
         
     | 
| 
      
 95 
     | 
    
         
            +
                        @context_kind = '.' + value         
         
     | 
| 
      
 96 
     | 
    
         
            +
                      end
         
     | 
| 
      
 97 
     | 
    
         
            +
                  
         
     | 
| 
      
 98 
     | 
    
         
            +
                      opt.on("--verbose", "-v",
         
     | 
| 
      
 99 
     | 
    
         
            +
                             "Display extra progress as we parse.") do |value|
         
     | 
| 
      
 100 
     | 
    
         
            +
                        @verbosity = 2
         
     | 
| 
      
 101 
     | 
    
         
            +
                      end
         
     | 
| 
      
 102 
     | 
    
         
            +
             
     | 
| 
      
 103 
     | 
    
         
            +
                      # No argument, shows at tail.  This will print an options summary.
         
     | 
| 
      
 104 
     | 
    
         
            +
                      # Try it and see!
         
     | 
| 
      
 105 
     | 
    
         
            +
                      opt.on_tail("-h", "--help", "Show this message") do
         
     | 
| 
      
 106 
     | 
    
         
            +
                        puts opts
         
     | 
| 
      
 107 
     | 
    
         
            +
                        exit
         
     | 
| 
      
 108 
     | 
    
         
            +
                      end
         
     | 
| 
      
 109 
     | 
    
         
            +
             
     | 
| 
      
 110 
     | 
    
         
            +
                      # Another typical switch to print the version.
         
     | 
| 
      
 111 
     | 
    
         
            +
                      opt.on_tail("--version", "Show version") do
         
     | 
| 
      
 112 
     | 
    
         
            +
                        puts "wlang version " << WLang::VERSION << " (c) University of Louvain, Bernard & Louis Lambeau"
         
     | 
| 
      
 113 
     | 
    
         
            +
                        exit
         
     | 
| 
      
 114 
     | 
    
         
            +
                      end
         
     | 
| 
      
 115 
     | 
    
         
            +
                  
         
     | 
| 
      
 116 
     | 
    
         
            +
                      opt.separator nil
         
     | 
| 
      
 117 
     | 
    
         
            +
                    end   
         
     | 
| 
      
 118 
     | 
    
         
            +
                
         
     | 
| 
      
 119 
     | 
    
         
            +
                    # handle arguments    
         
     | 
| 
      
 120 
     | 
    
         
            +
                    rest = opts.parse!(argv)
         
     | 
| 
      
 121 
     | 
    
         
            +
                    if rest.length<1 or rest.length>2
         
     | 
| 
      
 122 
     | 
    
         
            +
                      puts opts
         
     | 
| 
      
 123 
     | 
    
         
            +
                      exit
         
     | 
| 
      
 124 
     | 
    
         
            +
                    end
         
     | 
| 
      
 125 
     | 
    
         
            +
                
         
     | 
| 
      
 126 
     | 
    
         
            +
                    # handle template file
         
     | 
| 
      
 127 
     | 
    
         
            +
                    @template_file = File.expand_path(rest[0])
         
     | 
| 
      
 128 
     | 
    
         
            +
                    raise("File '#{@template_file}' not readable")\
         
     | 
| 
      
 129 
     | 
    
         
            +
                      unless File.file?(@template_file) and File.readable?(@template_file)
         
     | 
| 
      
 130 
     | 
    
         
            +
             
     | 
| 
      
 131 
     | 
    
         
            +
                    # handle context file
         
     | 
| 
      
 132 
     | 
    
         
            +
                    if rest.length==2
         
     | 
| 
      
 133 
     | 
    
         
            +
                      @context_file = rest[1]
         
     | 
| 
      
 134 
     | 
    
         
            +
                      raise("File '#{@context_file}' not readable")\
         
     | 
| 
      
 135 
     | 
    
         
            +
                        unless File.file?(@context_file) and File.readable?(@context_file)
         
     | 
| 
      
 136 
     | 
    
         
            +
                    end
         
     | 
| 
      
 137 
     | 
    
         
            +
                
         
     | 
| 
      
 138 
     | 
    
         
            +
                    # handle template dialect
         
     | 
| 
      
 139 
     | 
    
         
            +
                    unless @template_dialect
         
     | 
| 
      
 140 
     | 
    
         
            +
                      extname = File.extname(@template_file)
         
     | 
| 
      
 141 
     | 
    
         
            +
                      @template_dialect = WLang::FILE_EXTENSIONS[extname]
         
     | 
| 
      
 142 
     | 
    
         
            +
                      raise("No known dialect for file extension '#{extname}'\n"\
         
     | 
| 
      
 143 
     | 
    
         
            +
                            "Known extensions are: " << WLang::FILE_EXTENSIONS.keys.join(", "))\
         
     | 
| 
      
 144 
     | 
    
         
            +
                        if @template_dialect.nil?
         
     | 
| 
      
 145 
     | 
    
         
            +
                    end
         
     | 
| 
      
 146 
     | 
    
         
            +
                
         
     | 
| 
      
 147 
     | 
    
         
            +
                    # handle context object
         
     | 
| 
      
 148 
     | 
    
         
            +
                    if @context_file
         
     | 
| 
      
 149 
     | 
    
         
            +
                      @context_object = WLang::load_data(@context_file, @context_kind)
         
     | 
| 
      
 150 
     | 
    
         
            +
                    end
         
     | 
| 
      
 151 
     | 
    
         
            +
                    
         
     | 
| 
      
 152 
     | 
    
         
            +
                    return self
         
     | 
| 
      
 153 
     | 
    
         
            +
                  end
         
     | 
| 
      
 154 
     | 
    
         
            +
              
         
     | 
| 
      
 155 
     | 
    
         
            +
                end # class Options  
         
     | 
| 
      
 156 
     | 
    
         
            +
             
     | 
| 
      
 157 
     | 
    
         
            +
              end # class WLangCommand
         
     | 
| 
      
 158 
     | 
    
         
            +
            end # module WLang
         
     | 
    
        data/test/sandbox.rb
    ADDED
    
    | 
         @@ -0,0 +1 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            puts "blambeau".to_sym
         
     | 
    
        data/test/test_all.rb
    ADDED
    
    
| 
         @@ -0,0 +1,111 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'test/unit'
         
     | 
| 
      
 2 
     | 
    
         
            +
            require 'wlang'
         
     | 
| 
      
 3 
     | 
    
         
            +
            module WLang
         
     | 
| 
      
 4 
     | 
    
         
            +
             
     | 
| 
      
 5 
     | 
    
         
            +
              # Tests the IntelligentBuffer class
         
     | 
| 
      
 6 
     | 
    
         
            +
              class AnagramBugsTest < Test::Unit::TestCase
         
     | 
| 
      
 7 
     | 
    
         
            +
                include IntelligentBuffer::Methods
         
     | 
| 
      
 8 
     | 
    
         
            +
               
         
     | 
| 
      
 9 
     | 
    
         
            +
                def test_on_anagram_spacing_policy
         
     | 
| 
      
 10 
     | 
    
         
            +
                  WLang::dialect("anagram") do
         
     | 
| 
      
 11 
     | 
    
         
            +
                    rule '=~' do |parser,offset|
         
     | 
| 
      
 12 
     | 
    
         
            +
                      match, reached = parser.parse(offset, "wlang/dummy")
         
     | 
| 
      
 13 
     | 
    
         
            +
                      block, reached = parser.parse_block(reached, "wlang/dummy")
         
     | 
| 
      
 14 
     | 
    
         
            +
             
     | 
| 
      
 15 
     | 
    
         
            +
                      # puts "Here is the block ==="
         
     | 
| 
      
 16 
     | 
    
         
            +
                      # puts "#{block.gsub(/ /, '.').gsub(/\n/, "\\n\n")}"
         
     | 
| 
      
 17 
     | 
    
         
            +
                      # puts "=== Here is the block"
         
     | 
| 
      
 18 
     | 
    
         
            +
             
     | 
| 
      
 19 
     | 
    
         
            +
                      [block, reached]
         
     | 
| 
      
 20 
     | 
    
         
            +
                    end
         
     | 
| 
      
 21 
     | 
    
         
            +
                  end
         
     | 
| 
      
 22 
     | 
    
         
            +
                  template = %q{
         
     | 
| 
      
 23 
     | 
    
         
            +
                    =~{String}{
         
     | 
| 
      
 24 
     | 
    
         
            +
                      this is an anagram template
         
     | 
| 
      
 25 
     | 
    
         
            +
                    }
         
     | 
| 
      
 26 
     | 
    
         
            +
                  }.gsub(/^ {8}/, '').strip
         
     | 
| 
      
 27 
     | 
    
         
            +
                  result = template.wlang_instantiate({}, "anagram")
         
     | 
| 
      
 28 
     | 
    
         
            +
                  assert IntelligentBuffer===result
         
     | 
| 
      
 29 
     | 
    
         
            +
            #      assert_equal("this is an anagram template", result)
         
     | 
| 
      
 30 
     | 
    
         
            +
             
     | 
| 
      
 31 
     | 
    
         
            +
                  template = %q{
         
     | 
| 
      
 32 
     | 
    
         
            +
                    =~{String}{
         
     | 
| 
      
 33 
     | 
    
         
            +
                      module MyModule
         
     | 
| 
      
 34 
     | 
    
         
            +
                      end
         
     | 
| 
      
 35 
     | 
    
         
            +
                    }
         
     | 
| 
      
 36 
     | 
    
         
            +
                  }.gsub(/^ {8}/, '').strip
         
     | 
| 
      
 37 
     | 
    
         
            +
                  result = template.wlang_instantiate({}, "anagram")
         
     | 
| 
      
 38 
     | 
    
         
            +
                  assert IntelligentBuffer===result
         
     | 
| 
      
 39 
     | 
    
         
            +
                  assert_equal("module MyModule\nend\n", result)
         
     | 
| 
      
 40 
     | 
    
         
            +
                end
         
     | 
| 
      
 41 
     | 
    
         
            +
                
         
     | 
| 
      
 42 
     | 
    
         
            +
                def test_missing_end_bug
         
     | 
| 
      
 43 
     | 
    
         
            +
                  WLang::dialect("anagram") do
         
     | 
| 
      
 44 
     | 
    
         
            +
                    rules WLang::RuleSet::Basic
         
     | 
| 
      
 45 
     | 
    
         
            +
                    rules WLang::RuleSet::Imperative
         
     | 
| 
      
 46 
     | 
    
         
            +
                    rule '=~' do |parser,offset|
         
     | 
| 
      
 47 
     | 
    
         
            +
                      match, reached = parser.parse(offset, "wlang/dummy")
         
     | 
| 
      
 48 
     | 
    
         
            +
                      match = parser.evaluate(match)
         
     | 
| 
      
 49 
     | 
    
         
            +
                      block, reached = parser.parse_block(reached, "wlang/dummy")
         
     | 
| 
      
 50 
     | 
    
         
            +
                      block = block.strip_block(block)
         
     | 
| 
      
 51 
     | 
    
         
            +
                      block = block.tabto(block,0)
         
     | 
| 
      
 52 
     | 
    
         
            +
                      parser.evaluate("matching_rules") << [match, block]
         
     | 
| 
      
 53 
     | 
    
         
            +
                
         
     | 
| 
      
 54 
     | 
    
         
            +
                      # puts "Here is the block ==="
         
     | 
| 
      
 55 
     | 
    
         
            +
                      # puts "#{block.gsub(/ /, '.').gsub(/\n/, "\\n\n")}"
         
     | 
| 
      
 56 
     | 
    
         
            +
                      # puts "=== Here is the block"
         
     | 
| 
      
 57 
     | 
    
         
            +
                
         
     | 
| 
      
 58 
     | 
    
         
            +
                      ["", reached]
         
     | 
| 
      
 59 
     | 
    
         
            +
                    end
         
     | 
| 
      
 60 
     | 
    
         
            +
                    rule '+~' do |parser,offset|
         
     | 
| 
      
 61 
     | 
    
         
            +
                      what, reached = parser.parse(offset, "wlang/dummy")
         
     | 
| 
      
 62 
     | 
    
         
            +
                      evaluated = parser.evaluate(what)
         
     | 
| 
      
 63 
     | 
    
         
            +
                      raise "Unexpected case, #{what} leads to nil" unless evaluated
         
     | 
| 
      
 64 
     | 
    
         
            +
                
         
     | 
| 
      
 65 
     | 
    
         
            +
                      rules = parser.evaluate("matching_rules")
         
     | 
| 
      
 66 
     | 
    
         
            +
                      found = rules.find {|r| r[0]===evaluated}
         
     | 
| 
      
 67 
     | 
    
         
            +
                      raise "Unexpected case: no match for #{what.class}" unless found
         
     | 
| 
      
 68 
     | 
    
         
            +
                
         
     | 
| 
      
 69 
     | 
    
         
            +
                      context = {"n" => evaluated, "matching_rules" => rules}
         
     | 
| 
      
 70 
     | 
    
         
            +
                      inst = found[1].wlang_instantiate(context, "anagram")
         
     | 
| 
      
 71 
     | 
    
         
            +
                      
         
     | 
| 
      
 72 
     | 
    
         
            +
                      inst2 = inst.gsub(/ /, '.').gsub(/\n/, "\\n\n")
         
     | 
| 
      
 73 
     | 
    
         
            +
                      # puts "Here is the inst ==="
         
     | 
| 
      
 74 
     | 
    
         
            +
                      # puts "#{inst2}"
         
     | 
| 
      
 75 
     | 
    
         
            +
                      # puts "=== Here is the inst"
         
     | 
| 
      
 76 
     | 
    
         
            +
                      
         
     | 
| 
      
 77 
     | 
    
         
            +
                      found = [inst, reached]
         
     | 
| 
      
 78 
     | 
    
         
            +
                    end
         
     | 
| 
      
 79 
     | 
    
         
            +
                  end
         
     | 
| 
      
 80 
     | 
    
         
            +
                  template = %Q{
         
     | 
| 
      
 81 
     | 
    
         
            +
                    =~{Array}{
         
     | 
| 
      
 82 
     | 
    
         
            +
                      module MyModule
         
     | 
| 
      
 83 
     | 
    
         
            +
                        *{n as c}{
         
     | 
| 
      
 84 
     | 
    
         
            +
                          +~{c}
         
     | 
| 
      
 85 
     | 
    
         
            +
                        }
         
     | 
| 
      
 86 
     | 
    
         
            +
                      end
         
     | 
| 
      
 87 
     | 
    
         
            +
                    }
         
     | 
| 
      
 88 
     | 
    
         
            +
                    =~{Integer}{
         
     | 
| 
      
 89 
     | 
    
         
            +
                      +{n}
         
     | 
| 
      
 90 
     | 
    
         
            +
                    }
         
     | 
| 
      
 91 
     | 
    
         
            +
                    +~{n}
         
     | 
| 
      
 92 
     | 
    
         
            +
                  }.gsub(/ {8}/,'').strip
         
     | 
| 
      
 93 
     | 
    
         
            +
                  context = {'n' => [10, 20, 30], 'matching_rules' => []}
         
     | 
| 
      
 94 
     | 
    
         
            +
                  result = template.wlang_instantiate(context, "anagram")
         
     | 
| 
      
 95 
     | 
    
         
            +
                
         
     | 
| 
      
 96 
     | 
    
         
            +
                  # template = template.gsub(/ /, '.').gsub(/\n/, "\\n\n")
         
     | 
| 
      
 97 
     | 
    
         
            +
                  # puts "Here is the template ==="
         
     | 
| 
      
 98 
     | 
    
         
            +
                  # puts "#{template}"
         
     | 
| 
      
 99 
     | 
    
         
            +
                  # puts "=== Here is the template"
         
     | 
| 
      
 100 
     | 
    
         
            +
                
         
     | 
| 
      
 101 
     | 
    
         
            +
                  # result = result.gsub(/ /, '.').gsub(/\n/, "\\n\n")
         
     | 
| 
      
 102 
     | 
    
         
            +
                  # puts "Here is the result ==="
         
     | 
| 
      
 103 
     | 
    
         
            +
                  # puts "#{result}"
         
     | 
| 
      
 104 
     | 
    
         
            +
                  # puts "=== Here is the result"
         
     | 
| 
      
 105 
     | 
    
         
            +
                  result = result.strip
         
     | 
| 
      
 106 
     | 
    
         
            +
                  expected = "module MyModule\n  10\n  \n  20\n  \n  30\n\nend"
         
     | 
| 
      
 107 
     | 
    
         
            +
                  assert_equal expected, result
         
     | 
| 
      
 108 
     | 
    
         
            +
                end
         
     | 
| 
      
 109 
     | 
    
         
            +
                
         
     | 
| 
      
 110 
     | 
    
         
            +
              end
         
     | 
| 
      
 111 
     | 
    
         
            +
            end
         
     | 
| 
         @@ -0,0 +1,52 @@ 
     | 
|
| 
      
 1 
     | 
    
         
            +
            require 'test/unit'
         
     | 
| 
      
 2 
     | 
    
         
            +
            require 'wlang'
         
     | 
| 
      
 3 
     | 
    
         
            +
            require 'wlang/test_utils'
         
     | 
| 
      
 4 
     | 
    
         
            +
            require 'wlang/rulesets/basic_ruleset'
         
     | 
| 
      
 5 
     | 
    
         
            +
            require 'wlang/rulesets/context_ruleset'
         
     | 
| 
      
 6 
     | 
    
         
            +
            require 'wlang/rulesets/buffering_ruleset'
         
     | 
| 
      
 7 
     | 
    
         
            +
             
     | 
| 
      
 8 
     | 
    
         
            +
            # Tests the Basic ruleset
         
     | 
| 
      
 9 
     | 
    
         
            +
            class WLang::BasicRuleSetTest < Test::Unit::TestCase
         
     | 
| 
      
 10 
     | 
    
         
            +
              include WLang::TestUtils
         
     | 
| 
      
 11 
     | 
    
         
            +
              
         
     | 
| 
      
 12 
     | 
    
         
            +
              # Installs a dialect on wlang
         
     | 
| 
      
 13 
     | 
    
         
            +
              def setup
         
     | 
| 
      
 14 
     | 
    
         
            +
                WLang::dialect "basic-test" do 
         
     | 
| 
      
 15 
     | 
    
         
            +
                  rules WLang::RuleSet::Basic
         
     | 
| 
      
 16 
     | 
    
         
            +
                  rules WLang::RuleSet::Context
         
     | 
| 
      
 17 
     | 
    
         
            +
                  rules WLang::RuleSet::Buffering
         
     | 
| 
      
 18 
     | 
    
         
            +
                end
         
     | 
| 
      
 19 
     | 
    
         
            +
              end
         
     | 
| 
      
 20 
     | 
    
         
            +
             
     | 
| 
      
 21 
     | 
    
         
            +
              # tests !{wlang/hosted} operator
         
     | 
| 
      
 22 
     | 
    
         
            +
              def test_execution
         
     | 
| 
      
 23 
     | 
    
         
            +
                tests = [
         
     | 
| 
      
 24 
     | 
    
         
            +
                  ["!{name}", "blambeau", {"name" => "blambeau"}],
         
     | 
| 
      
 25 
     | 
    
         
            +
                  ["!{!{var}}", "blambeau", {"var" => "name", "name" => "blambeau"}],
         
     | 
| 
      
 26 
     | 
    
         
            +
                  ["!{'hello'.upcase}", "HELLO", {}]
         
     | 
| 
      
 27 
     | 
    
         
            +
                ]
         
     | 
| 
      
 28 
     | 
    
         
            +
                tests.each do |t|
         
     | 
| 
      
 29 
     | 
    
         
            +
                  template, expected, context = t
         
     | 
| 
      
 30 
     | 
    
         
            +
                  result = template.wlang(context, "basic-test")
         
     | 
| 
      
 31 
     | 
    
         
            +
                  assert_equal(expected, result) 
         
     | 
| 
      
 32 
     | 
    
         
            +
                end
         
     | 
| 
      
 33 
     | 
    
         
            +
              end
         
     | 
| 
      
 34 
     | 
    
         
            +
                
         
     | 
| 
      
 35 
     | 
    
         
            +
              # Tests recursive_application rule
         
     | 
| 
      
 36 
     | 
    
         
            +
              def test_recursive_application
         
     | 
| 
      
 37 
     | 
    
         
            +
                tests = [
         
     | 
| 
      
 38 
     | 
    
         
            +
                  ["#={code}{%{wlang/dummy}{+{variable}}}"\
         
     | 
| 
      
 39 
     | 
    
         
            +
                   "%!{basic-test with variable: 'hello'}{+{code}}", "hello"],
         
     | 
| 
      
 40 
     | 
    
         
            +
                  ["<<={data.rb as context}"\
         
     | 
| 
      
 41 
     | 
    
         
            +
                   "#={code}{%{wlang/dummy}{+{author}}}"\
         
     | 
| 
      
 42 
     | 
    
         
            +
                   "%!{basic-test using context}{+{code}}", "blambeau"]
         
     | 
| 
      
 43 
     | 
    
         
            +
                ]
         
     | 
| 
      
 44 
     | 
    
         
            +
                tests.each do |test|
         
     | 
| 
      
 45 
     | 
    
         
            +
                  template, expected = test
         
     | 
| 
      
 46 
     | 
    
         
            +
                  template = relative_template(template, "basic-test", __FILE__)
         
     | 
| 
      
 47 
     | 
    
         
            +
                  result = template.instantiate()
         
     | 
| 
      
 48 
     | 
    
         
            +
                  assert_equal(expected, result)
         
     | 
| 
      
 49 
     | 
    
         
            +
                end
         
     | 
| 
      
 50 
     | 
    
         
            +
              end
         
     | 
| 
      
 51 
     | 
    
         
            +
              
         
     | 
| 
      
 52 
     | 
    
         
            +
            end # class WLang::BasicRuleSetTest
         
     |