03:19
<ljharb>
is it weird to anyone else that https://tc39.es/ecma262/#sec-property-descriptor-specification-type says that an empty Record is a Property Descriptor?
03:33
<bakkot>
it is, though
03:33
<bakkot>
that's so Object.defineProperty(foo, 'bar', {}) works
07:32
<ljharb>
i mean i get that an empty object has to work in a number of places. but since { enumerable: true } isn't a property descriptor record either (that'd be { [[Enumerable]]: true }) i'm not sure why an empty record needs to be one
17:24
<bakkot>
if you look at how Object.defineProperty works it basically mechanically converts the object into a spec record by copying over each of the relevant fields https://tc39.es/ecma262/multipage/ecmascript-data-types-and-values.html#sec-topropertydescriptor
17:26
<bakkot>
and then passing it to definePropertyOrThrow which switches on presence of various fields
17:32
<bakkot>
it could work some other way but the reason an empty record is a property descriptor record is to allow it to be written this way
17:34
<bakkot>
I think if we were writing it today we'd probably avoid having optional fields in the record, which we usually avoid, but it would require a bit more machinery
17:45
<ljharb>
I definitely understand why it's written this way
17:46
<ljharb>
i'm wondering if it would be cleaner to special-case "no fields" rather than having the bottom type of all records be Property Descriptor
18:01
<bakkot>
ah
18:01
<bakkot>
I prefer not to; I don't think of records as really sharing types
18:02
<bakkot>
it's not like you come across a random record with no context in the spec; they're always being passed around between specific algorithms which make it clear what kind of thing they're working with
18:25
<Michael Ficarra>
lmao is this guy trying to save disk space on GitHub's servers? https://github.com/tc39/ecma262/pull/3478#issuecomment-2589138113
18:25
<Michael Ficarra>
who does this?
18:29
<jmdyck>
Maybe he's saving space locally then pushing to github?
18:45
<jmdyck>
ljharb: Given Let _e_ be Record {}. If _e_ is a Property Descriptor, then ..., are you thinking that the condition would succeed?
18:47
<ljharb>
who does this?
I’ve encountered many; some are the rare folks who use the PRs and issues tab, and are also stuck on the idea of “clean”, meaning they want to remove things from the list, and that requires closing PRs. In this case, i think he looks at his own profile and says “ick, too many forks” and tries to “clean” them up. But this is like the third time this guy;s done this with the same 262 PR, so i dunno what he’s thinking
18:47
<ljharb>
ljharb: Given Let _e_ be Record {}. If _e_ is a Property Descriptor, then ..., are you thinking that the condition would succeed?
it does, right now, to my reading.
18:49
<jmdyck>
So you think "is a Foo Record" could be true of any record, regardless of how created, as long as it only has fields that a Foo Record can have?
18:51
<ljharb>
yes, we have structural not nominal typing on records
18:53
<jmdyck>
What suggests this to you?
18:56
<bakkot>
well, we do for property descriptors specifically per the introductory paragraph of https://tc39.es/ecma262/multipage/ecmascript-data-types-and-values.html#sec-property-descriptor-specification-type
18:57
<bakkot>
I think/hope that everywhere else in the spec the difference would be never be observable; we're not really switching on the types of internal records much (ever?)
18:58
<shu>
there're a few places around Reference Records, and class fields
18:59
<shu>
but yes i also hope the difference is never observable
19:00
<shu>
more specifically i hope, for named records, we never create record literals without the name (but with all the fields) and use it like the named records
19:02
<bakkot>
ooh, found one but it's silly https://tc39.es/ecma262/multipage/fundamental-objects.html#sec-symbol.for
19:02
<jmdyck>
bakkot: you're saying that that intro paragraph says that property descriptors have structural not nominal typing?
19:03
<shu>
oh boo but at least it's right above the table
19:03
<bakkot>

jmdyck that's my reading of it yes:

Property Descriptor values may be further classified as data Property Descriptors and accessor Property Descriptors based upon the existence or use of certain fields

19:04
<bakkot>
I also really dislike the reference to the ambient "GlobalSymbolRegistry List" in Symbol.for
19:05
<bakkot>
I'm sure Michael Ficarra dislikes it more
19:05
<jmdyck>
oh, the second paragraph, hm.
19:05
<bakkot>
oh sorry yes
19:06
<shu>
but it really is so global
19:06
<shu>
it transcends all realms
19:06
<bakkot>
yes but we should <dfn> it or something at the very least
19:07
<shu>
yeah, and... i guess we should also build in locking?
19:07
<bakkot>
oh yeah fun
19:07
<bakkot>
we can just handwave that
19:07
<bakkot>
actually, would it be observable? they're not structured-cloneable
19:09
<jmdyck>
(GlobalSymbolRegistry is called out in MF's 2724: https://github.com/tc39/ecma262/issues/2724#issuecomment-1093579455)
19:09
<bakkot>
ah, good good
19:10
<shu>
i didn't realize they weren't actually
19:10
<bakkot>
symbols aren't cloneable at all
19:10
<bakkot>
it's a bit silly
19:10
<bakkot>
registered symbols probably should be
19:11
<bakkot>
https://html.spec.whatwg.org/multipage/structured-data.html#structuredserializeinternal step 5
19:12
<shu>
that is eminently silly yes
19:19
<jmdyck>
I think you can read the second para of 6.2.6 as classifying values that you've already established are Property Descriptors. So it doesn't address whether an empty schema-less Record qualifies as a Property Descriptor.
19:22
<bakkot>
right, yeah; by "we have structural typing for property descriptors" I meant only "within the property descriptor type we have structural typing", not that we have it for discriminating property descriptors from other kinds of things
19:32
<jmdyck>
okay, so to the question of Given Let _e_ be Record {}. If _e_ is a Property Descriptor, then ..., does the condition succeed, your answer is (roughly): the spec doesn't say, and I hope there's never a case where we'd need an answer ?
19:33
<jmdyck>
(such a case would be an editorial error?)
19:34
<bakkot>
correct
19:35
<bakkot>
though the one case in Symbol.for needs fixing for that to be strictly true
19:35
<jmdyck>
i don't understand the Symbol.for example.
19:36
<jmdyck>
what exactly?
19:36
<bakkot>
we create a record with specific fields, and do not call out that it is a GlobalSymbolRegistry Record, and then put it in a list of GlobalSymbolRegistry Records
19:36
<shu>
jmdyck, specifically step 5
19:36
<bakkot>
this implies that an anonymous Record having the fields of a GlobalSymbolRegistry Record is sufficient to be a GlobalSymbolRegistry Record, i.e., it implies we are using structural typing for records
19:44
<jmdyck>
gotcha.
19:45
<jmdyck>
In my static analysis, that's the only error of that kind.
19:47
<jmdyck>
It goes back to ES6.
19:51
<jmdyck>
Re GlobalSymbolRegistry transcending all realms, see https://github.com/tc39/ecma262/issues/824
19:54
<shu>
wait, does each agent have its own registry?
19:54
<shu>
i thought it was truly global to the agent cluster, but i may be misremembering since i also thought this was observable (but turns out it isn't due to structured cloning not working)
19:54
<bakkot>
all we know is "The GlobalSymbolRegistry is an append-only List that is globally available. It is shared by all realms."
19:55
<bakkot>
I would parse "globally available" as meaning "across agent" but it's not observable so /shrug
20:12
<jmdyck>
AWB thought that GlobalSymbolRegistry was per-Agent: https://github.com/tc39/ecma262/issues/882#issuecomment-293334655, which was quoted in issue 1357.
21:11
<ljharb>
even without that section, if i make a record and give it all the slots of an X record, how is it not thus an X record?
21:12
<Michael Ficarra>
@ljharb we just try not to do that
21:12
<Michael Ficarra>
if something needs a record of a particular kind, I construct it with that in mind
21:22
<jmdyck>
ljharb: you have a mental model in which it is, I have a mental model in which it is not. The spec appears to be non-committal / allow both.
21:22
<ljharb>
i totally get we'd try not to do that
21:23
<ljharb>
but if the spec allows for structural, then it can't possibly be nominal, mental models notwithstanding
21:24
<ljharb>
(i'm fine with making one or the other explicit, to be clear)
21:25
<jmdyck>
how do you figure "can't possibly be"?
21:25
<ljharb>
because if it's allowed to not be nominal, then it's not nominal?
21:26
<ljharb>
iow there's nothing in the spec preventing me passing a normal empty record where a Property Descriptor is allowed, ∴ it's allowed
21:26
<jmdyck>
the editors might prevent that.
21:27
<jmdyck>
deeming it an editorial error.
21:31
<bakkot>
anything pattern the spec doesn't do or give meaning to is something with no meaning
21:32
<bakkot>
it's a document
21:32
<bakkot>
you can write whatever words you want but you can't rely on readers knowing what those words mean unless they're unambiguous or spelled out
21:33
<bakkot>
you can't just say "I knew it was structural when I was writing it so it's fine" and assume the reader will also know that
21:34
<jmdyck>
Whether the spec lets you pass a schemaless empty Record where a Property Descriptor is allowed is basically the same question as whether the condition succeeds in Let _e_ be Record {}. If _e_ is a Property Descriptor, then .... And bakkot says the spec does not answer that question, and shouldn't need to.
21:34
<bakkot>
fortunately as long as we never introduce a place where it would matter we'll never have to clarify which it is
21:40
<jmdyck>
If you could write arbitrary pseudo-code and some procedure had to give you the result, then the question would need to have an answer. But that's not the situation.
21:48
<jmdyck>
My static-analysis code would complain if it saw such a thing. Don't know about esmeta.
22:03
<ljharb>
downstream specs could, though, so i still think it's worth clarifying
23:00
<bakkot>
downstream specs can do lots of things we'd rather they not do but we shouldn't make it easier for them
23:28
<ljharb>
i agree, i'm not asking for that :-)
23:29
<ljharb>
i'm asking to make it harder for them by making records nominal, and/or making an empty record not be a property descriptor
23:50
<bakkot>
explicitly making records nominal would let downstream specs rely on records being nominal, which we don't want them to do
23:54
<jmdyck>
hm. what would it look like to "rely on records being nominal"? What could someone write that you wouldn't like?
23:59
<ljharb>
ok, then explicitly make them structural, and still make an empty record not be anything