3

I am new to Deno and TypeScript but have plenty of experience using NodeJs and Javascript, I have stumbled on an issue of sorts, that I could have easily sorted out in NodeJs by simply adding global into the mix, however, that shows to be rather difficult in Deno for some reason.

I want to declare the First variable that should be available globally everywhere without need to import it. (sort of like Deno variable is available)

Here is an example of the code I'm trying to get running:

/// index.ts
import { FirstClass } from './FirstClass.ts';

global.First = new FirstClass();

await First.commit();

/// FirstClass.ts
import { SecondClass } from './SecondClass.ts';
export class FirstClass {
  constructor() {}
  async commit() {
    const second = new SecondClass();

    await second.comment();
  }
}

/// SecondClass.ts
export class SecondClass {
  constructor() {}
  comment() {
    console.log(First); // Should log the FirstClass
  }
}

I would run this code like this: deno run index.ts

Tibor Huđik
  • 35
  • 1
  • 4
  • 2
    What is the purpose of a global variable? Is it to avoid importing that variable into each module that needs it? I personally don't use any global variables. Instead, I create that variable in a module and export it. Then, in all the other modules that need that variable, I import it. What's the main thing you get from having a global in these days of ES modules? – Lonnie Best Jun 09 '20 at 19:13

1 Answers1

3

The global object in Deno is: window / globalThis

window.First = new FirstClass();

For TypeScript compiler errors see: How do you explicitly set a new property on `window` in TypeScript?

declare global {
    var First: FirstClass
    interface Window { First: any; }
}

window.First = new FirstClass();
await First.commit();
Tibor Huđik
  • 35
  • 1
  • 4
Marcos Casagrande
  • 37,983
  • 8
  • 84
  • 98
  • 1
    Yes it does work. The problem is that `TypeScript` is not letting you because `First` "does not exist" on type `Window`. So `//@ts-ignore` or fix your types, just replace all your `.ts` files with `.js` and you see that it works. – Marcos Casagrande Jun 09 '20 at 16:30
  • When I declare it in the `index.ts` file, then the only error I get is from the SecondClass where it says that it cannot find it. – Tibor Huđik Jun 09 '20 at 16:46
  • 1
    See my code to how to declare global variables in TypeScript. But that's a TypeScript limitation, the original answer is still correct. – Marcos Casagrande Jun 09 '20 at 16:50
  • It's not globally declared if I cannot access it in the SecondClass without `//@ts-ignore` – Tibor Huđik Jun 09 '20 at 16:55
  • 1
    It's globally declared, TypeScript not recognizing global variables it's a TypeScript problem. That's how you declare a global variable in Deno, using `window.X` which is equivalent to node `global.X`. How to use global variables in TypeScript is another question, and I already linked you to the answer. Run it in JavaScript and you'll see that's globally declared in Deno. – Marcos Casagrande Jun 09 '20 at 16:59
  • How would I fix the problem with TypeScript so it can be accessible within SecondClass without `//@ts-ignore`? – Tibor Huđik Jun 09 '20 at 17:37
  • 1
    Ideally using `global.d.ts` which Deno doesn't support yet https://github.com/denoland/deno/issues/5270 Or use `window.First` – Marcos Casagrande Jun 09 '20 at 18:14
  • 1
    This is perfect example of why I don't use typescript. It is more of a burden than it is worth. My deno projects are exclusively javascript and due to this fact they start quicker. Typescript is the slowest thing in deno. All else is blazing fast. – Lonnie Best Jun 09 '20 at 19:23
  • Global means to me after setting it global it is accessible everywhere as a variable, not as a property. That does not seem possible in deno since the globals dont get extracted inside the modules and are not available inside imported submodules. –  Apr 28 '21 at 09:50