* Emit a Go interface for a discriminated union (anyOf with const discriminator).
(
typeName: string,
discriminator: GoDiscriminatorInfo,
ctx: GoCodegenCtx,
description?: string,
experimental = false
)
| 1765 | * Emit a Go interface for a discriminated union (anyOf with const discriminator). |
| 1766 | */ |
| 1767 | function emitGoFlatDiscriminatedUnion( |
| 1768 | typeName: string, |
| 1769 | discriminator: GoDiscriminatorInfo, |
| 1770 | ctx: GoCodegenCtx, |
| 1771 | description?: string, |
| 1772 | experimental = false |
| 1773 | ): void { |
| 1774 | if (ctx.generatedNames.has(typeName)) return; |
| 1775 | ctx.generatedNames.add(typeName); |
| 1776 | |
| 1777 | const discriminatorProp = discriminator.property; |
| 1778 | const mapping = discriminator.mapping; |
| 1779 | const unionVariants = [...discriminator.variants].sort((left, right) => compareGoTypeNames(left.typeName, right.typeName)); |
| 1780 | const discGoName = toGoFieldName(discriminatorProp); |
| 1781 | const discriminatorMethodName = goDiscriminatorMethodName(typeName, discriminatorProp, discGoName, unionVariants, ctx); |
| 1782 | let discEnumName: string | undefined; |
| 1783 | let discGoType = "bool"; |
| 1784 | if (discriminator.valueKind === "string") { |
| 1785 | const discValues = [...mapping.keys()].filter((value): value is string => typeof value === "string"); |
| 1786 | discEnumName = getOrCreateGoEnum( |
| 1787 | typeName + discGoName, |
| 1788 | discValues, |
| 1789 | ctx, |
| 1790 | `${discGoName} discriminator for ${typeName}.`, |
| 1791 | undefined, |
| 1792 | false, |
| 1793 | experimental |
| 1794 | ); |
| 1795 | discGoType = discEnumName; |
| 1796 | } |
| 1797 | |
| 1798 | const unmarshalFuncName = goUnexportedFunctionName("unmarshal", typeName); |
| 1799 | const rawDataName = `Raw${typeName}${ctx.discriminatedUnionRawVariantSuffix ?? "Data"}`; |
| 1800 | const hasRawVariant = discriminator.valueKind === "string"; |
| 1801 | const markerName = toGoUnexportedIdentifier(typeName); |
| 1802 | ctx.discriminatedUnions.set(typeName, { typeName, unmarshalFuncName }); |
| 1803 | |
| 1804 | const lines: string[] = []; |
| 1805 | if (description) { |
| 1806 | pushGoCommentForContext(lines, description, ctx); |
| 1807 | } |
| 1808 | if (experimental) { |
| 1809 | pushGoExperimentalTypeComment(lines, typeName, ctx); |
| 1810 | } |
| 1811 | lines.push(`type ${typeName} interface {`); |
| 1812 | lines.push(`\t${markerName}()`); |
| 1813 | lines.push(`\t${discriminatorMethodName}() ${discGoType}`); |
| 1814 | lines.push(`}`); |
| 1815 | lines.push(``); |
| 1816 | |
| 1817 | const ambiguousGroupsByVariantTypeName = new Map<string, GoDiscriminatedUnionVariant[]>(); |
| 1818 | for (const groupVariants of mapping.values()) { |
| 1819 | if (groupVariants.length <= 1) continue; |
| 1820 | const sortedGroupVariants = [...groupVariants].sort((left, right) => compareGoTypeNames(left.typeName, right.typeName)); |
| 1821 | for (const variant of groupVariants) { |
| 1822 | ambiguousGroupsByVariantTypeName.set(variant.typeName, sortedGroupVariants); |
| 1823 | } |
| 1824 | } |
no test coverage detected
searching dependent graphs…