all files / lib/genlex/ token.js

100% Statements 56/56
100% Branches 0/0
100% Functions 33/33
100% Lines 56/56
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 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 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 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 136 137 138 139 140 141 142                                        2480×     554×         5717×       8016×               542×       541×     4083×       4080×                 15684× 15676× 12639×   3037×                 5717×         542×     4083×             8017×         3021×     4634×              
/*
 * Parsec
 * https://github.com/d-plaindoux/parsec
 *
 * Copyright (c) 2016 Didier Plaindoux
 * Licensed under the LGPL2 license.
 */
 
module.exports = (function () {
    
    'use strict';
    
    var parser = require('../parsec/parser.js'),
        response = require('../parsec/response.js'),
        option = require('../data/option.js');
    
    function Token() {
    }
    
    Token.prototype.keyword = function() {
        return option.none();
    };
      
    Token.prototype.ident =  function() {
        return option.none();
    };
        
    Token.prototype.number =  function() {
        return option.none();
    };
        
    Token.prototype.string =  function() {
        return option.none();
    };
        
    Token.prototype.char =  function() {
        return option.none();
    };
    
    function TKKeyword(value) {
        this.value = value;
    }
    
    TKKeyword.prototype = new Token();
    
    TKKeyword.prototype.keyword = function() {
        return option.some(this.value);
    };
    
    function TKIdent(value) {
        this.value = value;
    }
    
    TKIdent.prototype = new Token();
    
    TKIdent.prototype.ident = function() {
        return option.some(this.value);
    };
    
    function TKNumber(value) {
        this.value = value;
    }
    
    TKNumber.prototype = new Token();
    
    TKNumber.prototype.number = function() {
        return option.some(this.value);
    };
    
    function TKString(value) {
        this.value = value;
    }
    
    TKString.prototype = new Token();
 
    TKString.prototype.string = function() {
        return option.some(this.value);
    };
    
    function TKChar(value) {
        this.value = value;
    }
    
    TKChar.prototype = new Token();    
    
    TKChar.prototype.char = function() {
        return option.some(this.value);
    };
    
    // (Token -> Option 'a) -> Parser 'a Token
    function literal(tokenise) {
        return parser.parse(function(input, index) {
           return input.get(index).map(function(value) {
               return tokenise(value).map(function(token){
                   return response.accept(token, input, index+1, true);
               }).orLazyElse(function() {
                   return response.reject(input.location(index), false);     
               });
           }).lazyRecoverWith(function() {
               return response.reject(input.location(index), false); 
           });
        });
    }
    
    return {
        builder: {
            keyword: function (value) {
                return new TKKeyword(value);
            },        
            ident: function (value) {
                return new TKIdent(value);
            },        
            number: function (value) {
                return new TKNumber(value);
            },        
            string: function (value) {
                return new TKString(value);
            },        
            char: function (value) {
                return new TKChar(value);
            }
        },
        parser: {
            keyword : literal(function(token) {
                return token.keyword();
            }),
            ident : literal(function(token) {
                return token.ident();
            }),
            number : literal(function(token) {
                return token.number();
            }),
            string : literal(function(token) {
                return token.string();
            }),
            char : literal(function(token) {
                return token.char();
            })
        }
    };
        
}());