Search code examples
angulartypescriptjavascript-debugger

Why is imported typescript function not available in Chrome Debugger


I'm trying to debug a method that I have imported into an Angular componenent. However some scope peculiarities around typescript are meaning that I cannot access an imported method via the debugger.

The method is the formatDuration method from date-fns. I want to be able to debug the method directly in the debugger however for some reason the method can't be accessed in the debugger and is always undefined.

import { Component } from '@angular/core'
import { formatDuration } from 'date-fns' // <= method imported

...

export class EntryComponent {

  duration:integer = 1000
  constructor() { }

  get duration():string{

    let duration_str = formatDuration({ seconds: this.duration },
                                      {format: ['hours', 'minutes']}
    )
    // I want to be able to jump in here and use the `formatDuration` method:
    debugger // <= debug statement

    return duration_str
  }
}

The debugger won't recognise the method when I try to call it

When I run the code above and attempt to call the formatDuration method in the console I get an error:

enter image description here

The method IS available to the code that's carrying it

I can't call the method using the debugger however if I remove the debugger statement it is being called successfully. For some reason, it's out of scope of the debugger though 🤷🏼‍♂️

Copying the method to a local variable makes it available...

get duration():string{

  let duration_str = formatDuration({ seconds: this.duration },
                                    {format: ['hours', 'minutes']}
  )
  // make a copy -------------
  let myVersion:any = formatDuration; 
  // -------------------------
  debugger // <= debug statement
  
  return duration_str
}

Running myVersion in the console now returns the function as expected:

enter image description here

Stackblitz demonstration

Here's a stackblitz app that shows the problem. Open your debugger before loading the page and then follow the instructions just before the debug line. The source code for the Stackblitz page is here.

What's happening with scopes such that I can't access the imported method directly?


Solution

  • You should check the compiled JS file, because this is what the console will target. This generally depends on the target in your tsconfig.json and/or the packaging system as well. Because you are using angular, the packaging is done with webpack. You can find your formatDuration function somewhere here:

    _date-fns__WEBPACK_IMPORTED_MODULE_1__.formatDuration
    

    The 1 can also be 2 or 0 or 100, you will have to check the closure in the Scope section of the debugger. It's usually in the closure which has as name the typescript file you are debugging. For example:

    Closure (./src/app/components/entry.component.ts)
    

    For example, here you can see the imports from a certain service in my application:

    example closure scope

    Obviously, if you use --prod, this will all be minified, and will make things a lot harder to trace :)