Question: I am trying to mock a very simple browser environment that mimics how browsers react to user's change in `location` variable. As far as I know, users can alter

* `self.location`
* `location`
* `document.location`
* `window.location`

one of those to navigate the current window by either

* assigning a string of url directly onto the variable (e.g. `self.location = 'http://www.google.com'`)
* or assigning a string onto `href` inside the location object (e.g. `self.location.href = 'http://www.google.com'`)
* or maybe explicitly instantiating a location object.

So my real question is how can I instantiate the browser environment to allow users to assign location variable is anyway they wish and let me retrieve the location variable later on? Sorry if this sounds stupid, (I've never coded in javascript before) but in real world circumstances, do browsers convert string data into location objects through macro or does Javascript have some sort of "implicit constructor" mechanism that can automatically invoke the constructor of a class just by assigning a value?

(I am aware that there are dom libraries available, but I find them quite an overkill as I am only interested in the navigating mechanism.)

Answer: 
Well, there are actually several different answers, here.

First, don't anticipate being on the same page, when retrieving the `location`.

If a user changed it's value, then your page will change (and your in-memory application with it), so you'd need to do state management using some form of storage (online/offline) there.

In terms of how the object actually works, that isn't exactly JS (in all cases).

Long story short, there's JavaScript the language, and then there's the DOM/BOM.

Document-Object Model and Browser-Object Model.  

The DOM is a set of functions/objects that let you interface with the HTML/CSS(as it applies to an element) of the page.

The BOM contains things that relate, not directly to the HTML, but to other parts of web functionality.

`console.log( );` is a good example.  

JS has no native `console` object or `Console` constructor. That's a part of the BOM that's added to a browser's environment, by the browser vendor (or third-party plugin), and is implementation a specific, with no real standard.

Same thing is true for URLs.  

JS has a global object (in the BOM, it's called `window`), but it doesn't have a `location` natively. 

So the implementation -- the "how", is hard to answer.  

Some browsers might do it in legitimate JS, while others do it in C++ or C, and old IE even had ActiveX components.

That said, new JS engines do have magic `get` / `set` methods which can perform actions, while you set data.
Cutting-edge JS even has Proxies, which are sort of like that, but on steroids (these won't be widely supported everywhere for a few years)...

But older JS engines didn't have those features in place in the native language, so they went off into some other language and wired things up to behave in ways that wouldn't have been supported in JS itself, but were needed to fill out the BOM/DOM.

these days, using a `.set` might be all you need to grab an instance of a constructor.

So in terms of setting up your own object with similar functionality, you could RegEx parse (or iterate pieces of) the value handed to you.  

On your object, you could have magic `get`/`set` methods assigned to a property name, where you could then, on a `set`, either modify all aspects of your current instance (based on value), or save a new instance to the var currently occupied by the old one, passing the new value to the constructor.

...but "where's the Location" constructor is a question that's not going to be answered in any simple way, without going browser by browser, version by version.
What you're looking for here is a getter/setter pair.

```
var window = {
  get location() {
    return {
      get href() { return "foo"; },
      set href() { /* change stored location data */; },

      get port() { return 80; },
      set port() { /* change stored location data */; },

      /* etc ... */
    };
  }
  set location() {
    // change stored location data
  }
};

```