@@ -96,17 +96,155 @@ class InitCallValue : public CompileTimeValue {
9696 std::vector<FunctionParameter> Parameters;
9797};
9898
99- // / A representation of a Builder pattern initialization expression
99+ // / A representation of a Builder pattern initialization expression. For
100+ // / example:
101+ // /
102+ // / @FooBuilder
103+ // / public static var foos: [Foo] {
104+ // / Foo(name: "foos.1")
105+ // / Foo(name: "foos.2")
106+ // / }
107+ // /
108+ // / In this example, the result builder type is FooBuilder
109+ // / The members are Foo(name: "foos.1") and Foo(name: "foos.2")
110+ // /
100111class BuilderValue : public CompileTimeValue {
101112public:
102- BuilderValue () : CompileTimeValue(ValueKind::Builder) {}
113+ enum MemberKind {
114+ Expression,
115+ Either,
116+ Optional,
117+ LimitedAvailability,
118+ Array,
119+ Unknown
120+ };
121+
122+ // / A base class for individual members being declared inside the result
123+ // / builder
124+ class BuilderMember {
125+ public:
126+ MemberKind getKind () const { return Kind; }
127+
128+ protected:
129+ BuilderMember (MemberKind MemberKind) : Kind(MemberKind) {}
130+
131+ private:
132+ MemberKind Kind;
133+ };
134+
135+ // / A basic expression that is defined inside the result builder. For example:
136+ // / {
137+ // / Foo(name: "1")
138+ // / }
139+ // /
140+ class SingleMember : public BuilderMember {
141+ public:
142+ SingleMember (std::shared_ptr<CompileTimeValue> Element)
143+ : BuilderMember(MemberKind::Expression), Element(Element) {}
144+
145+ static bool classof (const BuilderMember *T) {
146+ return T->getKind () == MemberKind::Expression;
147+ }
148+
149+ std::shared_ptr<CompileTimeValue> getElement () const { return Element; }
150+
151+ private:
152+ std::shared_ptr<CompileTimeValue> Element;
153+ };
154+
155+ // / A member that represents when the individual values are defined by
156+ // / iterating over an array. For example:
157+ // / for i in 1...3 {
158+ // / Foo(name: "MyFooProviderInferred.foos.Array.\(i)")
159+ // / }
160+ // /
161+ class ArrayMember : public BuilderMember {
162+ public:
163+ ArrayMember (std::vector<std::shared_ptr<BuilderMember>> Elements)
164+ : BuilderMember(MemberKind::Array), Elements(Elements) {}
165+
166+ static bool classof (const BuilderMember *T) {
167+ return T->getKind () == MemberKind::Array;
168+ }
169+
170+ std::vector<std::shared_ptr<BuilderMember>> getElements () const {
171+ return Elements;
172+ }
173+
174+ private:
175+ std::vector<std::shared_ptr<BuilderMember>> Elements;
176+ };
177+
178+ // / A member that is defined conditionally. It can be of the following types:
179+ // /
180+ // / 1. A regular if-else condition
181+ // / if condition {
182+ // / Foo(name: "1")
183+ // / } else {
184+ // / Foo(name: "2")
185+ // / }
186+ // /
187+ // / 2. An optional
188+ // / if condition {
189+ // / Foo(name: "1")
190+ // / }
191+ // /
192+ // / 3. Limited availability
193+ // / if #available(macOS 99, *) {
194+ // / Foo(name: "1")
195+ // / Foo(name: "2")
196+ // / }
197+ // /
198+ class ConditionalMember : public BuilderMember {
199+ public:
200+ ConditionalMember (MemberKind MemberKind,
201+ std::vector<std::shared_ptr<BuilderMember>> IfElements,
202+ std::vector<std::shared_ptr<BuilderMember>> ElseElements)
203+ : BuilderMember(MemberKind), IfElements(IfElements),
204+ ElseElements (ElseElements) {}
205+
206+ static bool classof (const BuilderMember *T) {
207+ auto Kind = T->getKind ();
208+ return (Kind == MemberKind::Either) ||
209+ (Kind == MemberKind::LimitedAvailability) ||
210+ (Kind == MemberKind::Optional);
211+ }
212+
213+ std::vector<std::shared_ptr<BuilderMember>> getIfElements () const {
214+ return IfElements;
215+ }
216+ std::vector<std::shared_ptr<BuilderMember>> getElseElements () const {
217+ return ElseElements;
218+ }
219+
220+ private:
221+ std::vector<std::shared_ptr<BuilderMember>> IfElements;
222+ std::vector<std::shared_ptr<BuilderMember>> ElseElements;
223+ };
224+
225+ BuilderValue (std::vector<std::shared_ptr<BuilderMember>> Members)
226+ : CompileTimeValue(ValueKind::Builder), ResultBuilderType(std::nullopt ),
227+ Members(Members) {}
228+
229+ BuilderValue (CustomAttr *ResultBuilderType,
230+ std::vector<std::shared_ptr<BuilderMember>> Members)
231+ : CompileTimeValue(ValueKind::Builder),
232+ ResultBuilderType(ResultBuilderType), Members(Members) {}
233+
234+ std::optional<CustomAttr *> getResultBuilderType () const {
235+ return ResultBuilderType;
236+ }
237+ std::vector<std::shared_ptr<BuilderMember>> getMembers () const {
238+ return Members;
239+ }
103240
104241 static bool classof (const CompileTimeValue *T) {
105242 return T->getKind () == ValueKind::Builder;
106243 }
107244
108245private:
109- std::vector<CompileTimeValue> Members;
246+ std::optional<CustomAttr *> ResultBuilderType;
247+ std::vector<std::shared_ptr<BuilderMember>> Members;
110248};
111249
112250struct TupleElement {
0 commit comments