Commit f0f5a630 authored by Eric Myhre's avatar Eric Myhre

schema compiler: last gasp of attempting this refactor.

I'm about to call it quits on this.  I'm not sure exactly where this
got off the rails, but I'm not happy about how its going, and
with this diff, I've reached enough "huh,hmm" moments that I think
it's going to end up being less work restarting on a cleaner approach
than it's going to be work finishing this, fixing all the bugs
resulting from the mess of maybeism, and then maintaining it.

Comments in the diff body show the exact moment of my exasperation
reaching a critical threshhold.

I'm really not happy with the golang typesystem today.

A more systematic review of this stack of diffs will follow in the
subsequent commit message.  It will be a merge-ignore commit.
parent 13d3707d
......@@ -153,6 +153,7 @@ func (c *Compiler) TypeStruct(name TypeName, fields list__StructField, rstrat St
}
//go:generate quickimmut -output=compiler_carriers.go -attach=Compiler list StructField
//go:generate quickimmut -output=compiler_carriers.go -attach=Compiler list StructFieldName
func (Compiler) MakeStructField(name StructFieldName, typ TypeReference, optional, nullable bool) StructField {
return StructField{nil, name, typ, optional, nullable}
......@@ -162,6 +163,28 @@ func (Compiler) MakeStructRepresentation_Map(fieldDetails map__StructFieldName__
return StructRepresentation_Map{nil, fieldDetails.x}
}
func (Compiler) MakeStructRepresentation_Tuple(fieldOrder *list__StructFieldName) StructRepresentation {
if fieldOrder == nil {
return StructRepresentation_Tuple{nil, nil}
}
return StructRepresentation_Tuple{nil, fieldOrder.x}
}
func (Compiler) MakeStructRepresentation_Stringpairs(innerDelim string, entryDelim string) StructRepresentation {
return StructRepresentation_Stringpairs{innerDelim, entryDelim}
}
func (Compiler) MakeStructRepresentation_Stringjoin(delim string, fieldOrder *list__StructFieldName) StructRepresentation {
if fieldOrder == nil {
return StructRepresentation_Stringjoin{nil, delim, nil}
}
return StructRepresentation_Stringjoin{nil, delim, fieldOrder.x}
}
func (Compiler) MakeStructRepresentation_Listpairs() StructRepresentation {
return StructRepresentation_Listpairs{}
}
//go:generate quickimmut -output=compiler_carriers.go -attach=Compiler map StructFieldName StructRepresentation_Map_FieldDetails
func (c *Compiler) TypeMap(name TypeName, keyTypeRef TypeName, valueTypeRef TypeReference, valueNullable bool, rstrat MapRepresentation) {
......
......@@ -37,6 +37,28 @@ func (b *list__StructField__Builder) Finish() list__StructField {
return list__StructField(v)
}
type list__StructFieldName struct {
x []StructFieldName
}
type list__StructFieldName__Builder list__StructFieldName
func (Compiler) MakeList__StructFieldName(ents ...StructFieldName) list__StructFieldName {
x := make([]StructFieldName, len(ents))
copy(x, ents)
return list__StructFieldName{x}
}
func (Compiler) StartList__StructFieldName(sizeHint int) list__StructFieldName__Builder {
return list__StructFieldName__Builder{make([]StructFieldName, 0, sizeHint)}
}
func (b *list__StructFieldName__Builder) Append(v StructFieldName) {
b.x = append(b.x, v)
}
func (b *list__StructFieldName__Builder) Finish() list__StructFieldName {
v := *b
b.x = nil
return list__StructFieldName(v)
}
type map__StructFieldName__StructRepresentation_Map_FieldDetails struct {
x map[StructFieldName]StructRepresentation_Map_FieldDetails
}
......
......@@ -39,10 +39,10 @@ func (schdmt Schema) Compile() (*schema.TypeSystem, []error) {
schema.TypeName(t2.FieldKeyType().String()),
t2.FieldValueType().TypeReference(),
t2.FieldValueNullable().Bool(),
t2.FieldRepresentation().compile(c),
t2.FieldRepresentation().flip(c),
)
// If the field typeReference is TypeDefnInline, that needs a chance to take additional action.
t2.FieldValueType().compile(c)
t2.FieldValueType().flip(c)
case TypeList:
c.TypeList(
schema.TypeName(tn.String()),
......@@ -50,7 +50,7 @@ func (schdmt Schema) Compile() (*schema.TypeSystem, []error) {
t2.FieldValueNullable().Bool(),
)
// If the field typeReference is TypeDefnInline, that needs a chance to take additional action.
t2.FieldValueType().compile(c)
t2.FieldValueType().flip(c)
case TypeStruct:
// Flip fields info from DMT to compiler argument format.
fields := make([]schema.StructField, t2.FieldFields().Length())
......@@ -63,21 +63,21 @@ func (schdmt Schema) Compile() (*schema.TypeSystem, []error) {
fdmt.FieldNullable().Bool(),
))
// If the field typeReference is TypeDefnInline, that needs a chance to take additional action.
fdmt.FieldType().compile(c)
fdmt.FieldType().flip(c)
}
// Flip the representaton strategy DMT to compiler argument format.
rstrat := func() schema.StructRepresentation {
switch r := t2.FieldRepresentation().AsInterface().(type) {
case StructRepresentation_Map:
return r.compile()
return r.flip()
case StructRepresentation_Tuple:
return r.compile()
return r.flip()
case StructRepresentation_Stringpairs:
return r.compile()
return r.flip()
case StructRepresentation_Stringjoin:
return r.compile()
return r.flip()
case StructRepresentation_Listpairs:
return r.compile()
return r.flip()
default:
panic("unreachable")
}
......@@ -100,17 +100,17 @@ func (schdmt Schema) Compile() (*schema.TypeSystem, []error) {
rstrat := func() schema.UnionRepresentation {
switch r := t2.FieldRepresentation().AsInterface().(type) {
case UnionRepresentation_Keyed:
return r.compile()
return r.flip()
case UnionRepresentation_Kinded:
return r.compile()
return r.flip()
case UnionRepresentation_Envelope:
return r.compile()
return r.flip()
case UnionRepresentation_Inline:
return r.compile()
return r.flip()
case UnionRepresentation_StringPrefix:
return r.compile()
return r.flip()
case UnionRepresentation_BytePrefix:
return r.compile()
return r.flip()
default:
panic("unreachable")
}
......@@ -134,14 +134,14 @@ func (schdmt Schema) Compile() (*schema.TypeSystem, []error) {
// If the typeReference is TypeDefnInline, create the anonymous type and feed it to the compiler.
// It's fine if anonymous type has been seen before; we let dedup of that be handled by the compiler.
func (dmt TypeNameOrInlineDefn) compile(c *schema.Compiler) {
func (dmt TypeNameOrInlineDefn) flip(c *schema.Compiler) {
switch dmt.AsInterface().(type) {
case TypeDefnInline:
panic("nyi") // TODO this needs to engage in anonymous type spawning.
}
}
func (dmt MapRepresentation) compile(c *schema.Compiler) schema.MapRepresentation {
func (dmt MapRepresentation) flip(c *schema.Compiler) schema.MapRepresentation {
switch rdmt := dmt.AsInterface().(type) {
case MapRepresentation_Map:
return schema.MapRepresentation_Map{}
......@@ -154,7 +154,7 @@ func (dmt MapRepresentation) compile(c *schema.Compiler) schema.MapRepresentatio
}
}
func (dmt StructRepresentation_Map) compile() schema.StructRepresentation {
func (dmt StructRepresentation_Map) flip() schema.StructRepresentation {
if !dmt.FieldFields().Exists() {
return schema.Compiler{}.MakeStructRepresentation_Map(schema.Compiler{}.MakeMap__StructFieldName__StructRepresentation_Map_FieldDetails())
}
......@@ -177,23 +177,49 @@ func (dmt StructRepresentation_Map) compile() schema.StructRepresentation {
return schema.Compiler{}.MakeStructRepresentation_Map(fields.Finish())
}
func (dmt StructRepresentation_Tuple) compile() schema.StructRepresentation {
func (dmt StructRepresentation_Tuple) flip() schema.StructRepresentation {
panic("TODO")
}
func (dmt StructRepresentation_Stringpairs) compile() schema.StructRepresentation {
func (dmt StructRepresentation_Stringpairs) flip() schema.StructRepresentation {
panic("TODO")
}
func (dmt StructRepresentation_Stringjoin) compile() schema.StructRepresentation {
panic("TODO")
func (dmt StructRepresentation_Stringjoin) flip() schema.StructRepresentation {
return schema.Compiler{}.MakeStructRepresentation_Stringjoin(
dmt.FieldJoin().String(),
func() (v []schema.StructFieldName) {
// Maybeism is carried forward here as a nil.
// - Precomputing the defaults would require looking at information up-tree, so we leave it to the Compiler to do later.
// - The difference between nil (meaning "default") and empty list is still significant; the latter should be able to cause validation errors.
// - The carrier types don't have an explicit maybe; a pointer and nil is used as poor maybe.
// ...
// OH, MY, GOD.
// The quickimmut things don't allow you to carry a nil around in a list.
// The mixture of how sentinels and maybes carry through dmt|carriers|precompile|compile is just insane.
//
// And yes: we do need to disambiguate versus zero-len list here: specifying it but being empty: that's an error.
// Fwiw: this is the only place in the whole schemaschema where this appears right now. There are no other optional lists nor optional maps.
// ... it keeps getting worse. we can't refer to the type so we can't use this helper function. lol.
if !dmt.FieldFieldOrder().Exists() {
return nil
}
for itr := dmt.FieldFieldOrder().Must().Iterator(); !itr.Done(); {
_, fn := itr.Next()
v = append(v, schema.StructFieldName(fn.String()))
}
return
}(),
)
}
func (dmt StructRepresentation_Listpairs) compile() schema.StructRepresentation {
func (dmt StructRepresentation_Listpairs) flip() schema.StructRepresentation {
panic("TODO")
}
func (dmt UnionRepresentation_Keyed) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_Keyed) flip() schema.UnionRepresentation {
ents := schema.Compiler{}.StartMap__String__TypeName(int(dmt.Length()))
for itr := dmt.Iterator(); !itr.Done(); {
k, v := itr.Next()
......@@ -202,22 +228,22 @@ func (dmt UnionRepresentation_Keyed) compile() schema.UnionRepresentation {
return schema.Compiler{}.MakeUnionRepresentation_Keyed(ents.Finish())
}
func (dmt UnionRepresentation_Kinded) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_Kinded) flip() schema.UnionRepresentation {
panic("TODO")
}
func (dmt UnionRepresentation_Envelope) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_Envelope) flip() schema.UnionRepresentation {
panic("TODO")
}
func (dmt UnionRepresentation_Inline) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_Inline) flip() schema.UnionRepresentation {
panic("TODO")
}
func (dmt UnionRepresentation_StringPrefix) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_StringPrefix) flip() schema.UnionRepresentation {
panic("TODO")
}
func (dmt UnionRepresentation_BytePrefix) compile() schema.UnionRepresentation {
func (dmt UnionRepresentation_BytePrefix) flip() schema.UnionRepresentation {
panic("TODO")
}
......@@ -44,7 +44,8 @@ type StructRepresentation_Map_FieldDetails struct {
}
type StructRepresentation_Tuple struct {
fieldOrder []StructFieldName
parent *TypeStruct // this one needs a pointer back up to figure out its defaults.
fieldOrder []StructFieldName // may be nil, which means "use default"
}
type StructRepresentation_Stringpairs struct {
......@@ -53,8 +54,9 @@ type StructRepresentation_Stringpairs struct {
}
type StructRepresentation_Stringjoin struct {
parent *TypeStruct // this one needs a pointer back up to figure out its defaults.
delim string
fieldOrder []StructFieldName
fieldOrder []StructFieldName // may be nil, which means "use default"
}
type StructRepresentation_Listpairs struct {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment