1

I´m trying to instantiate two classes in a beforeEach in Jest. For some reason, these two variables seem to be inaccessible for the rest of the functions. Is it a closure problem?

describe('Restaurant', () => {
    let instance: Restaurant;


    beforeEach(() => {
        instance = new Restaurant();
        const Client1 = new User(Client1)
        const Client2 = new User(Client2);
    });

    it('serve two clients', () => {
Here Client1 and Client2 are not accesible
        expect(() => instance.serve(Client1, Client2)).toEqual(1);
    });



});
skyboyer
  • 22,209
  • 7
  • 57
  • 64
  • Possible duplicate of [How to pass variable from beforeEach hook to tests in jest?](https://stackoverflow.com/questions/52397708/how-to-pass-variable-from-beforeeach-hook-to-tests-in-jest) – Brian Adams Sep 12 '19 at 18:32

1 Answers1

1

Client1 and Client2 are only visible in the scope of beforeEach. Move your variables up to the instance variable, and "global" scope of the test, and it should work.

describe('Restaurant', () => {
    let instance: Restaurant;
    let Client1 = null;
    let Client2 = null;

    beforeEach(() => {
        instance = new Restaurant();
        Client1 = new User(Client1)
        Client2 = new User(Client2);
    });

    it('serve two clients', () => {
Here Client1 and Client2 are not accesible
        expect(() => instance.serve(Client1, Client2)).toEqual(1);
    });



});

Edit with a little scope information.

class WorkWithPeople {

    let person = new person();

    //Here we have a function scope or local scope. It has acces to the parent scope where "person" is defined (much like your instance).
    ClonePerson = (person) => {

        //This is a local scope variable - the clone. The "clone" is only available within the scope of ClonePerson
        let clone = this.person;
    }

    SetAgeForPerson = () => {
        this.person.age = 25; // We can do this because "person" is defined in the parent scope of SetAgeForPerson. 
        clone.age = 25; // We cannot do this, because clone is defined in the scope of "ClonePerson", a sibling scope to SetAgeForPerson.
    }

    ClonePersonAndSetAge = () => {

        let clone = this.person;


        //This scope is defined as a child scope of "ClonePersonAndSetAge" - so it has access to all the parents scopes
        let ChildSopeSetAge = () => {
            clone.age = 25; 

            this.person.name = "Jack Overflow"; // We can do this because person is available in a parent scope.
        }

    }

    //Most important to notice is that ALL scopes defined in a sibling are "invisible"
}

You can try and visualize it either a as a branching structure, or boxes within boxes: Branch visualization

Square visualization

Dennis
  • 909
  • 4
  • 13
  • 30
  • Thank you. Why does this happen, though? Since they are all inside "describe", shouldn´t variables declared in beforeEach be accesible to all the functions? – Edgardo Minotauro Sep 12 '19 at 12:07
  • In general scopes can be considered in two categories; global and local, although I think the terms are slightly confusing to begin with. A variable defined in the global scope is in the JS file, outside any functions. Local scopes(function scopes) are more interesting. Basically it means that "you" can only see what's in its own scope. Visible scopes can be considered parents of a function, or children of a function; but not siblings. So `describe` is a parent scope of both `beforeEach` and `it`, so it works. But `it` is a sibling scope to `beforeEach` so they can't peak into each other. – Dennis Sep 13 '19 at 06:22
  • @EdgardoMinotauro the `const` and `let` kewords are block scoped. As Dennis says this means they are only accessible within their own scope. For example you cant access a variable declared here `if(condition) {const variable = "value"}` outside of the if-block. However if you do: `const variable = "value"; if(condition){console.log(variable)}` it will work just fine because the block scope wraps your if-statement. A more elaborate explanation is available here https://blog.usejournal.com/var-let-and-const-hoisting-and-scope-8860540031d1 – Jonas Johansson Sep 13 '19 at 07:03