jsdoc-typescript-plugin icon indicating copy to clipboard operation
jsdoc-typescript-plugin copied to clipboard

Nested generic types not properly parsed

Open jumpinjackie opened this issue 9 years ago • 5 comments

The current regex used for parsing generic types

/(.+)(.\<)(.+)\>/

Currently breaks down on nested types

eg. Foo.<Array.<Bar>>

Ultimately, we need the regex to only care about the outermost .< and > instances

jumpinjackie avatar Mar 09 '16 15:03 jumpinjackie

I don't think a regex can do this, you need a real parser. I can write this if you want.

icholy avatar May 15 '16 15:05 icholy

Here's a pegjs grammar that will parse the types

Type 
    = GenericType
    / UnionType
    / ArrayType
    / SimpleType

NonUnionType
    = GenericType
    / ArrayType
    / SimpleType

NonArrayType
    = GenericType
    / "(" _ type:UnionType ")" {
        return type;
    }
    / SimpleType

UnionType
    = first:NonUnionType _ rest:UnionTypeRest+ {
        return {
            kind: "union",
            types: [first].concat(rest)
        };
    }

UnionTypeRest
    = "|" _ type:NonUnionType {
        return type;
    }

GenericType
    = name:Ident "."? "<" _ params:GenericTypeParams _ ">" {
        return {
            kind: "generic",
            name: name,
            parameters: params
        }
    }

GenericTypeParams
    = first:Type? _ rest:GenericTypeParamsRest* {
        return first ? [first].concat(rest) : rest;
    }

GenericTypeParamsRest
    = "," _ type:Type {
        return type;
    }

SimpleType
    = name:Ident {
        return {
            kind: "simple",
            name: text()
        };
    }

ArrayType
    = type:NonArrayType "[]" {
        return {
            kind: "generic",
            name: "Array",
            params: [type]
        }
    }

Ident
  = [a-zA-Z$_-] [a-zA-Z0-9$_-]* {
    return text();
  }

_ "whitespace"
  = [ \t\n\r]*

The result of parsing Foo.<Array.<Bar>> is:

{
   "kind": "generic",
   "name": "Foo",
   "parameters": [
      {
         "kind": "generic",
         "name": "Array",
         "parameters": [
            {
               "kind": "simple",
               "name": "Bar"
            }
         ]
      }
   ]
}

icholy avatar Sep 20 '16 20:09 icholy

parsing Entity|Entity[]|EntityCollection|DataSource|ImageryLayer|Promise.<Entity|Entity[]|EntityCollection|DataSource|ImageryLayer> gives:

{
   "kind": "union",
   "types": [
      {
         "kind": "simple",
         "name": "Entity"
      },
      {
         "kind": "generic",
         "name": "Array",
         "params": [
            {
               "kind": "simple",
               "name": "Entity"
            }
         ]
      },
      {
         "kind": "simple",
         "name": "EntityCollection"
      },
      {
         "kind": "simple",
         "name": "DataSource"
      },
      {
         "kind": "simple",
         "name": "ImageryLayer"
      },
      {
         "kind": "generic",
         "name": "Promise",
         "parameters": [
            {
               "kind": "union",
               "types": [
                  {
                     "kind": "simple",
                     "name": "Entity"
                  },
                  {
                     "kind": "generic",
                     "name": "Array",
                     "params": [
                        {
                           "kind": "simple",
                           "name": "Entity"
                        }
                     ]
                  },
                  {
                     "kind": "simple",
                     "name": "EntityCollection"
                  },
                  {
                     "kind": "simple",
                     "name": "DataSource"
                  },
                  {
                     "kind": "simple",
                     "name": "ImageryLayer"
                  }
               ]
            }
         ]
      }
   ]
}

icholy avatar Sep 20 '16 20:09 icholy

Hi @icholy could you provide a pull request for this? PegJS sounds very useful.

jumpinjackie avatar Sep 21 '16 02:09 jumpinjackie

Looks like #83 closes this.

icholy avatar Jul 06 '17 18:07 icholy