guest271314 (2019-06-15T21:50:02.000Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name
of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just
pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code the identifer ```y``` does not exist. That is, unless there was an
expected presumption that ```y``` was defined globally prior to the
```const y = 1;``` declaration at the next line. Even then a variable
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration
`userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before
initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```

On Sat, Jun 15, 2019 at 9:37 PM Ron Buckton <Ron.Buckton at microsoft.com>
wrote:

> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name
> of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just
> pointing to the identifier.
>
>
>
> *From:* guest271314 <guest271314 at gmail.com>
> *Sent:* Friday, June 14, 2019 10:03 PM
> *To:* Ron Buckton <Ron.Buckton at microsoft.com>
> *Cc:* es-discuss at mozilla.org
> *Subject:* Re: Re: What do you think about a C# 6 like nameof()
> expression for
>
>
>
> > I’m not sure I understand what you mean by “false-positive” in this
> instance.
>
>
>
> Was referring to
>
>
>
> const x = nameof y; // "y"
>
> const y = 1;
>
>
>
> Where ```y``` is ```undefined``` an error is not expected to be thrown? Is
> ```y``` declared globally, using ```const``` or ```let```, or not at all?
> The use case  described by OP
>
>
>
> function func1(param1, param2, param3, userName, param4, param5) {
>
>    if (userName == undefined) {
>
>        throw new ArgumentNullError(nameof userName); // `ArgumentNullError`
>
> is a custom error, derived from `Error`, composes error message like
>
> "Argument cannot be null: userName".
>
>    }
>
> checks if ```userName``` was ```undefined``` before using ```nameof```.
> If error checking is a substantial portion of the proposal, why should an
> error (```y``` being ```undefined``` though referenced) be ignored when
> referencing an undefined identifier though concentrate on coercing a name
> from a different potentially undefined property?
>
>
>
> Consider this case:
> ```
> const someObject = { value: 1 };
> function setValue(value /*1*/) {
>   if (typeof value /*2*/ !== "number") throw new TypeError(`Number
> expected: ${nameof value /*3*/}`);
>   someObject["value" /*4*/] = value /*5*/;
> }
> ```
>
> If you rename the parameter `value` of the function `setValue` in an
> editor with a rename refactoring, you want to rename the symbols at 1, 2,
> 3, and 5, but not the string at 4.
>
>
>
> Not gathering the purpose or value of ```nameof``` usage in that case. If
> the value is not a "number" then why does the value or name matter?
>
>
>
> Since the primary use case appears to be an editor environment, why cannot
> the editor be programmed to recognize the custom JavaScript ```nameof````
> function or operator? Then it would not matter if this board concurred with
> the ```nameof``` functionality or not. Both CLI and GUI editors (and
> JavaScript) are generally extensible. FWIW, some time ago incorporated
> features into gedit for HTML templates; should be a similar process to
> create custom scripts for the various editor environments where users rely
> on such programs for code composition; now simply write the code by hand
> and test in different environments, without taking the time to customize or
> rely on an editor - take the time to test the code where the code will
> actually be run where errors, if any, can be evaluated in the context in
> which a specific output is expected. To each their own. What needs to be
> implemented outside of what the users which advocate for ```nameof```
> cannot implement themselves?
>
>
>
> As mentioned earlier do not rely on "an editor with name refactoring" to
> compose code. The code has to be tested (outside of the editor
> environments) anyway. Test the code itself, here, not the editor.
>
>
>
> On Fri, Jun 14, 2019 at 9:49 PM Ron Buckton <Ron.Buckton at microsoft.com>
> wrote:
>
> I’m not sure I understand what you mean by “false-positive” in this
> instance.
>
>
>
> Consider this case:
>
>
>
> ```
>
> const someObject = { value: 1 };
>
> function setValue(value /*1*/) {
>
>   if (typeof value /*2*/ !== "number") throw new TypeError(`Number
> expected: ${nameof value /*3*/}`);
>
>   someObject["value" /*4*/] = value /*5*/;
> }
>
> ```
>
>
>
> If you rename the parameter `value` of the function `setValue` in an
> editor with a rename refactoring, you want to rename the symbols at 1, 2,
> 3, and 5, but not the string at 4.
>
>
>
> Ron
>
>
>
> *From:* guest271314 <guest271314 at gmail.com>
> *Sent:* Friday, June 14, 2019 2:43 PM
> *To:* Ron Buckton <Ron.Buckton at microsoft.com>
> *Cc:* es-discuss at mozilla.org
> *Subject:* Re: Re: What do you think about a C# 6 like nameof()
> expression for
>
>
>
> How is that behaviour related to the use cases presented by OP? Would such
> behaviour not lead to false-positive relevant to the 2 use cases?
>
>
>
> On Fri, Jun 14, 2019 at 9:36 PM Ron Buckton <Ron.Buckton at microsoft.com>
> wrote:
>
> > `nameof whatever` → `Object.keys({ whatever })[0]`, but I'm a bit
> confused why it'd be better to type `nameof foo` in code, rather than
> `'foo'` - if you change `foo` to `bar`, you have to change both of them
> anyways.
>
>
>
> If you are using an editor that supports rename refactoring, its generally
> easier to rename the symbol `foo` and have all references (including
> `nameof foo`) be updated. You cannot safely automatically rename `'foo'` to
> `'bar'` since an editor or language service cannot guarantee that by the
> string `'foo'` you meant “the text of the identifier `foo`”.
>
>
>
> *From:* es-discuss <es-discuss-bounces at mozilla.org> *On Behalf Of *Jordan
> Harband
> *Sent:* Friday, June 14, 2019 2:29 PM
> *To:* guest271314 <guest271314 at gmail.com>
> *Cc:* es-discuss <es-discuss at mozilla.org>
> *Subject:* Re: Re: What do you think about a C# 6 like nameof()
> expression for
>
>
>
> `nameof whatever` → `Object.keys({ whatever })[0]`, but I'm a bit confused
> why it'd be better to type `nameof foo` in code, rather than `'foo'` - if
> you change `foo` to `bar`, you have to change both of them anyways.
>
>
>
> On Fri, Jun 14, 2019 at 1:31 PM guest271314 <guest271314 at gmail.com> wrote:
>
> Am neither for nor against the proposal. Do not entertain "like"s or
> "dislike"s in any field of endeavor. Am certainly not in a position to
> prohibit anything relevant JavaScript. Do what thou wilt shall be the whole
> of the Law.
>
> Have yet to view a case where code will be "broken" by ```nameof``` not
> being a JavaScript feature. "robustness", as already mentioned, is a
> subjective adjective that is not capable of being objectively evaluated as
> to code itself. That description is based on preference or choice.
>
>
>
> In lieu of the proposal being specificed, use the posted code example of
> ```Object.keys()``` that "works".
>
>
>
> ```
>
> function func1({userName = void 0} = {}) {
>   console.assert(userName !== undefined, [{userName}, 'property needs to
> be defined'])
> }
>
> ```
>
>
>
> provides a direct indication that the property value is required to be
> defined. Note that the example code posted thus far does not first check if
> ```options``` is passed at all, for which ```nameof``` will not provide any
> asssitance.
>
>
>
> Usually try to meet requirement by means already available in FOSS
> browsers. Have no interest in TypeScript or using an IDE.
>
>
>
> FWIW, have no objection to the proposal.
>
>
>
> On Fri, Jun 14, 2019 at 7:53 PM Stas Berkov <stas.berkov at gmail.com> wrote:
>
> guest271314, what is you point against `nameof` feature?
>
> If you don't like it - don't use it. Why prohibit this feature for
> those who find it beneficial?
>
> I see `nameof` beneficial in following cases
>
> Case 1. Function guard.
> ```
> function func1(options) {
> ...
>    if (options.userName == undefined) {
>        throw new ParamNullError(nameof options.userName); //
> `ParamNullError` is a custom error, derived from `Error`, composes
> error message like "Parameter cannot be null: userName".
>  // `Object.keys({options.userName})[0]` will not work here
>    }
> }
> ```
>
> Case 2. Accessing property extended info
> Those ES functions that accept field name as string.
> e.g.
> ```
> const descriptor1 = Object.getOwnPropertyDescriptor(object1, 'property1');
> ```
> vs
> ```
> const descriptor1 = Object.getOwnPropertyDescriptor(object1, nameof
> object1.property1);
>  // `Object.keys({options1.property1})[0]` will not work here
> ```
> 2nd variant (proposed) has more chances not to be broken during
> refactoring (robustness).
>
> It would make devs who use IDE more productive and make their life
> easier. Why not give them such possiblity and make them happy?
>
> _______________________________________________
> es-discuss mailing list
> es-discuss at mozilla.org
> https://mail.mozilla.org/listinfo/es-discuss
> <https://nam06.safelinks.protection.outlook.com/?url=https%3A%2F%2Fmail.mozilla.org%2Flistinfo%2Fes-discuss&data=02%7C01%7CRon.Buckton%40microsoft.com%7C161337d6ad7645d030a408d6f14ecaf8%7C72f988bf86f141af91ab2d7cd011db47%7C1%7C0%7C636961718057711545&sdata=JqYVgJrShIjaF33XEIFFj3WlUo2i4e8nzU1uGXf6qCk%3D&reserved=0>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.mozilla.org/pipermail/es-discuss/attachments/20190615/461624d5/attachment-0001.html>
guest271314 at gmail.com (2019-06-15T22:13:35.802Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code 

```
const x = nameof y; // "y"
const y = 1;
```

the identifer ```y``` does not exist. 

Was there an expected presumption that ```y``` was defined _globally_ in the code prior to the
```const y = 1;``` declaration at the next line (which would be a _different_ ```y``` variable than the variable on the next line declared with ```const```)?

Does the example code actually expect the ```const``` declaration ```y``` on the next line to be capable of being referenced on the current line _before_ the declaration ("initialization") on the next line occurs in the code?

A variable 
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case (referencing ```const``` variable _before_ declaration or initialization)

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration `userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```
guest271314 at gmail.com (2019-06-15T22:02:38.487Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code 

```
const x = nameof y; // "y"
const y = 1;
```

the identifer ```y``` does not exist. 

Was there an expected presumption that ```y``` was defined _globally_ in the code prior to the
```const y = 1;``` declaration at the next line (which would be a _different_ ```y``` variable than the variable on the next line declared with ```const```)?

Does the example code actually expect the ```const``` declaration ```y``` on the next line to be capable of being referenced on the current line _before_ the declaration ("initialization") on the next line occurs in the code?

A variable 
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration `userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```
guest271314 at gmail.com (2019-06-15T21:59:24.445Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code 

```
const x = nameof y; // "y"
const y = 1;
```

the identifer ```y``` does not exist. 

Was there an expected presumption that ```y``` was defined _globally_ in the code prior to the
```const y = 1;``` declaration at the next line (which would be a _different_ ```y``` variable than the variable on the next line declared with ```const```)?

Does the example code actually expect the ```const``` declaration ```y``` on the next line to be capable of being referenced before the declaration ("initialization")?

A variable
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration `userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```
guest271314 at gmail.com (2019-06-15T21:54:52.615Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code 

```
const x = nameof y; // "y"
const y = 1;
```

the identifer ```y``` does not exist. 

That is, unless there was an
expected presumption that ```y``` was defined _globally_ prior to the
```const y = 1;``` declaration at the next line - not referring to a variable that does not yet exist on the next line?

A variable
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration
`userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before
initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```
guest271314 at gmail.com (2019-06-15T21:52:06.196Z)
> It doesn’t matter what the *value* of ‘y’ is, just what the lexical name of `y` is. `nameof` wouldn’t refer to `y` as an expression, its just pointing to the identifier.

Was not referring to the _value_ of ```y```. At that point in the example
code the identifer ```y``` does not exist. 

That is, unless there was an
expected presumption that ```y``` was defined globally prior to the
```const y = 1;``` declaration at the next line. 

Even then a variable
declared using ```const``` cannot be referenced before "lexical
declaration" or "initialization". That fact can be utilized for an
alternative approach to meet requirement of "Case 1. Function guard.".
Tested at Chromium 76 and Firefox 69. Have not used MS browser (or
browserstack) in some time. Have not tried the code at Safari either,
though the code is capable of adjustment for any JavaScript environment
which throws a ```ReferenceError``` under the same case

```
function func1(param1, param2, param3, userName, param4, param5) {
  if (userName === undefined) {
    try {
      // throws ReferenceError
      // Firefox 69: ReferenceError: "can't access lexical declaration
`userName' before initialization"
      // Chromium 76: ReferenceError: Cannot access 'userName' before
initialization
      const userName = userName;
    } catch (e) {
      // match identifier at Firefox, Chromium ReferenceError message
      // adjust RegExp for IE/Edge, Safari, etc.
      const nameof = e.message.match(/(?!`|')[^\s]+(?=')/g).pop();
      throw new Error(`"Argument cannot be null: ${nameof}"`);
    }
  } else {
    // do stuff
    console.log(userName);
  }
}

try {
  func1(1, 2, 3); // throws error
} catch (e) {
  console.error(e); // get name of variable identifier
}

try {
  func1(1, 2, 3, 4); // logs userName at console
} catch (e) {
  console.error(e); // should not be reached
}
```