Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TypeError: Cannot read property 'flags' of undefined #84

Closed
frankebersoll opened this issue Apr 8, 2016 · 19 comments
Closed

TypeError: Cannot read property 'flags' of undefined #84

frankebersoll opened this issue Apr 8, 2016 · 19 comments
Assignees

Comments

@frankebersoll
Copy link

When building our project with minification enabled, we get this:

[18:40:31] TypeError: Cannot read property 'flags' of undefined
    at IdentifierInfo.isPrivateProperty (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1284:53)
    at BundleMinifier.canShortenIdentifier (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1781:28)
    at BundleMinifier.processIdentifierInfo (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1760:18)
    at BundleMinifier.shortenContainerIdentifiers (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1742:18)
    at BundleMinifier.shortenIdentifiers (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1712:14)
    at BundleMinifier.minify (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1685:14)
    at BundleMinifier.transform (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1504:21)
    at BundleCompiler.compile (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:2457:41)
    at Project.buildWorker (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:2659:44)
    at Project.build (/Users/Frank/Entwicklung/node/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:2576:32)
franks-macbook:Exceptionless.JavaScript Frank$ gulp typescript.node

Looks like "A property has a value declaration" isn't true in every case, but I don't know enough about the AST to understand what's going on here.

The current symbol looks like this:

SymbolObject {
  flags: 134217732,
  name: 'prototype',
  parent: 
   SymbolObject {
     flags: 32,
     name: 'Configuration',
     declarations: [ [Object] ],
     exports: 
      { prototype: [Circular],
        _defaultSettings: [Object],
        defaults: [Object] },
     members: 
      { defaultTags: [Object],
        defaultData: [Object],
        enabled: [Object],
        environmentInfoCollector: [Object],
        errorParser: [Object],
        lastReferenceIdManager: [Object],
        log: [Object],
        moduleCollector: [Object],
        requestInfoCollector: [Object],
        submissionBatchSize: [Object],
        submissionAdapter: [Object],
        submissionClient: [Object],
        settings: [Object],
        storage: [Object],
        queue: [Object],
        _plugins: [Object],
        __constructor: [Object],
        _apiKey: [Object],
        apiKey: [Object],
        isValid: [Object],
        _serverUrl: [Object],
        serverUrl: [Object],
        _dataExclusions: [Object],
        _userAgentBotPatterns: [Object],
        dataExclusions: [Object],
        addDataExclusions: [Object],
        userAgentBotPatterns: [Object],
        addUserAgentBotPatterns: [Object],
        plugins: [Object],
        addPlugin: [Object],
        removePlugin: [Object],
        setVersion: [Object],
        setUserIdentity: [Object],
        userAgent: [Object],
        useSessions: [Object],
        useReferenceIds: [Object],
        useLocalStorage: [Object],
        useDebugLogger: [Object] },
     valueDeclaration: 
      NodeObject {
        kind: 217,
        pos: 29933,
        end: 42727,
        flags: 2,
        parent: [Object],
        decorators: undefined,
        modifiers: [Object],
        name: [Object],
        typeParameters: undefined,
        heritageClauses: [Object],
        members: [Object],
        symbol: [Circular],
        localSymbol: [Object],
        nextContainer: [Object],
        id: 90264 },
     parent: 
      SymbolObject {
        flags: 512,
        name: '"exceptionless.node.min"',
        declarations: [Object],
        exports: [Object],
        valueDeclaration: [Object],
        id: 56518 },
     id: 55548 },
  id: 56470 }
@ToddThomson
Copy link
Owner

@frankebersoll The current symbol flag value is 134217732. This is a combination of SymbolFlags.Prototype + SymbolFlags.Property. The symbol dump indicates that you have something like

Configuration.prototype.someProperty = somePropertyValue;

I realize that "prototype" is a reserved word and thus cannot be shortened. I will review how reserved words are treated in TsProject.

I will need to add a test for this usage and investigate. Perhaps you can provide a code snippet from your project for this purpose.

I will resolve this issue early next week.

@frankebersoll
Copy link
Author

Hey Todd,

you can use this commit to reproduce the issue:

exceptionless/Exceptionless.JavaScript@113155c

Cheers and have a nice weekend!

@ToddThomson
Copy link
Owner

@frankebersoll I don't use git command line, so I am not sure how to download the source you are referring to above. I tried downloading the features/build branch, but I cannot get it to compile without error. Please let me know what to download to reproduce this issue. Thanks.

@ToddThomson
Copy link
Owner

@frankebersoll I've been able to recreate this issue by downloading exceptionless.javascript release 1.3.2 and modifying it slightly.
While is is obvious that the 'prototype' property cannot be shortened, I want to make sure that TsProject handles assignment to the 'prototype' properly.
It may be the case that your PR fixes this issue, but I have a feeling that the general fix will take a bit more - I just can't be sure until I write a test scenario.

@ToddThomson
Copy link
Owner

@frankebersoll This is an interesting issue. It is not straight forward!

@ToddThomson
Copy link
Owner

@frankebersoll I've opened an issue with the TypeScript project microsoft/TypeScript#8024

I need to resolve the TypeScript issue before I can complete fixing your issue.

@ToddThomson
Copy link
Owner

@frankebersoll @niemyjski I believe the solution to this issue can be handled by simply checking for a null valueDeclaration. However, as I thought, there are issue(s) that (may) result from this. TypeScript 1.8.9 does not resolve the Type for this in functions that are assigned to object.prototype (well, they are resolved to any). This leads to property identifiers not having associated symbols. TsProject uses these unique identifier symbols to shorten all occurrences of a given identifier.
Since you make an assignment to the Configuration.prototype.UseLocalStorage in your initialization code, which references the this.storage property in Configuration, the identifier storage in this case would not have a symbol and would not be shortened (iff the Configuration.storage identifier was private and was shortened ).
Now, I know that Configuration.storage in your specific case is public, so the identifier would not be shortened and thus no runtime error would be caused by minification. However, in general object properties can be marked as private and are thus candidates for shortening which would then result in runtime errors if they are accessed through the object prototype functions.
So, in the short term, I can patch TsProject to check for a null valueDeclaration in the appropriate places. However if you access object properties or methods in functions that are assigned to the object prototype you must mark them as public.
Please let me know what you think.

@ToddThomson
Copy link
Owner

@frankebersoll @niemyjski I've written some experimental code to resolve the Type for this when it is contained in a function that has been assigned to a class object prototype. I am not sure why TypeScript does not do this ( there prob. is a reason which will become apparent when they answer my issue ).
Are you in a rush to have this issue resolved?

@niemyjski
Copy link
Contributor

@ToddThomson I don't think we are in any big hurry but we are looking to switch from uglify to the new stuff soon.

@niemyjski
Copy link
Contributor

I don't say this enough but I really appreciate all the work you do!

@ToddThomson
Copy link
Owner

@niemyjski Thanks!
I am ready to release TsProject version 1.2.1. It will contain the fix for this issue. It will also include type resolution for this within functions that are assigned to the object prototype property.

@ToddThomson
Copy link
Owner

This issue has been addressed in release 1.2.1. Thank-you for your input!

@niemyjski
Copy link
Contributor

Awesome!!

@frankebersoll
Copy link
Author

Great stuff, thank you so much!

@ToddThomson
Copy link
Owner

@frankebersoll @niemyjski You're welcome.
The minification feature is pretty new. It is used to build TsProject itself, so it does work quite well (better than all the current javascript minifiers). If you do run into any issues I should be able to address them quickly. Good luck and happy coding!

@niemyjski
Copy link
Contributor

It looks like we are still hitting this issue. I'll work on getting more information.

@niemyjski
Copy link
Contributor

niemyjski commented Apr 12, 2017

@ToddThomson do you know if any progress has been made on this, it looks like it's the same exact issue that we ran into before (Just working on upgrading us to latest typescript https://github.com/exceptionless/Exceptionless.JavaScript/tree/feature/latest-ts)


[TsProject] Building bundle:  src/exceptionless-nodespec
[22:44:46] 'typescript.test' errored after 2.55 s
[22:44:46] TypeError: Cannot read property 'flags' of undefined
    at Object.getBaseTypes (/Users/blake/Code/Exceptionless.JavaScript/node_modules/typescript/lib/typescript.js:28239:37)
    at R.U (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:34088)
    at R.Q (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:33804)
    at /Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:32840
    at Array.forEach (native)
    at _loop_1 (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:32685)
    at R.O (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:33198)
    at V.bb (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:42564)
    at V.Y (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:41067)
    at Object.src (/Users/blake/Code/Exceptionless.JavaScript/node_modules/tsproject/tsproject.min.js:1:45967)

Seems to only happen when were running gulp typescript.test

@niemyjski
Copy link
Contributor

I think this has something to do with how we export functions in our tests:

export function describeStorage(name: string,
                                storageFactory: (maxItems?: number) => IStorage,
                                beforeEachCallback?: () => void,
                                recreateStorage: boolean = false) {

The passed in type to typescript.getBaseTypes(type) has an intrinsicName of unknown. and the symbol object is just the function name we export in the previous stack frame

@niemyjski
Copy link
Contributor

Kinda getting the feeling that it's expecting my functions to be exported from a class, and they are not (they are just test scripts)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants