 I stumbled upon this on Stack Overflow, and I'll read the original post, I'll have a few things to say, and then I'll get to my answer. Roughly that. Let's get into it. So he's asking about the builder pattern in IDA. I'm new to IDA and not very proficient in the way object orientation is handled in IDA. I'd like to know if it is possible to implement a builder-like pattern in IDA. The pattern is quite common in the Java programming language. And for those not familiar, he's basically wanting to do this. Build pattern is a sort of extension of the fluent design pattern. I'll get into explaining that more later. But basically it's a type of approach to construction of composite types. And I just want to say, please do not ever implement an add a library using this design pattern. IDA has an approach to this that is considerably better. This approach is meant for languages that do not have the default variables and is why Java utilizes it. That being said, I do think this is an example that would be great to learn from. And so unlike some of the answers that just completely misunderstand. Actually, you know what? Let's downvote that because that's bullshit. This does not require the compiler to know anything about the objects and construct a builder around them. That's just not how this works. My answer. So yes, this is possible. I strongly recommend you do not go with this approach though. It has very bad performance problems, not to mention is harder to maintain. That being said, it is in fact possible and should be possible in any language with dispatching. Maybe there are a few extra restrictions to that or maybe it's allowable in a few more things. I saw this question less than half an hour ago, so I haven't had much time to think about it. But it seems like dispatching is the primary constraint required for this to be possible. Actually, you know what? It might just be a syntax thing. But you usually only see method syntax in languages that support dispatching. So it might just be a syntax thing. Anyways, as I was saying, it's accomplished by an extension to the fluent pattern which uses an intermediary type. And we'll get into this. I'll switch the window over to VS Code in just a bit. Here's the package where this behavior is implemented. We have two types, person and person builder. Person is meant as an immutable or read-only form of the type. Whereas person builder is the mutable form. Immutability of person is accomplished by the property pattern. This is because EIDA doesn't have a read-only modifier for fields. And so the only way to make something read-only in EIDA is to make the record private and to expose these as functions that take no values. That they just return the value that you're interested in. Now I do take a little bit further advantage of this by returning a string. And actually the mutators, they do accept a string as well. But under the hood, these are unbounded strings just because we don't know how long the name is going to be or the place of birth. But this makes it appear as if it's using the simpler type. So it's just sort of a convenience thing around one of EIDA's quirks. The two interesting things you have here though that make it separate from other approaches is... Well actually let's cover the mutators or the setters first. You'll notice unlike the typical setter pattern, we're not actually modifying the dispatcher. We're not modifying the collie. Rather what we're doing is returning a new instance of it. And this essentially makes it the fluent pattern. And in fact I would largely view the builder pattern as an extension of the fluent pattern. I'm not sure if it's considered that formally. I don't really care much for studying formal language design. But I am familiar with these concepts. That also means don't be afraid to correct me if I'm slightly off on these categorizations. But the two interesting things which separate this from the fluent design approach is this and this. Builder does the conversion from... No it doesn't convert. Builder sets up the person builder type, prepares it for the rest of the calls. So this can be considered a constructor for the person builder itself with the rest of it acting like a constructor for the person. Whereas build takes the person builder and converts it back to a person. Now the one thing we will need to do since the add a language does not directly support this design pattern is have both of these types with the fields inside them duplicated. The exact types may be able to vary a little bit depending on exactly what you're doing. But for starters I'd recommend just having them exact copies of each other. You can restrict that down a little bit after you get everything working. And yeah under the hood there's really not a lot going on. You can see these literally just directly return the field after converting it to a string. The builder function just initializes everything to empty unbounded strings. I think there's an actual value for that but I can't remember what it's called right now because I haven't been doing add a programming in a while. So I just put that in there but it's fine. And each of these mutators so like the first name it'll take the value that's passed into it and set that appropriately. But then for all the other values it just copies whatever was passed into it. So technically you could just because of how this code is written set first name multiple times. There is a way to check for that so that repeated mutations are not allowed. But just because of the way this is set up in general after the final call to build since you'll have a person object and the person doesn't have any mutators defined for it it just simply won't work after that point. Once you call the build function it's just set in stone. It is immutable. One thing that I'll point out now that had to be done is because both person builder and person are defined as tagged objects or classes as most languages would know them. They're not exactly though. It's dispatching upon both types and that is not allowable because where do you put it? Which one do you associate it with? You can't be dispatching from two types at the same time. One of the simplest ways to get around that is to have one of the parameters possibly the return parameter but in this case I opted for the input parameter being of a class-wide type and that prevents it from being dispatching upon that type. This is not the only approach to make it only dispatching on one type. This is just the one I went with. I'm not going to cover that in this video. I just wanted to show how the build property works tonight. But then for our test code we have just the construction of it. So we define P as a person, call builder, pass the first name as Bob, pass the last name as Saget, play the place. I'm losing my ability to speak. I set the place of birth as Philadelphia, Pennsylvania because at least according to Wikipedia that's where he was born and then finally call build. Now everything from this point up to this point is not the appropriate type. Everything up until everything through here is mutable so you can continue to make changes. Like I said you could, based on how the code was already written you could reassign first name to something else. I really don't recommend that and I'll be showing you how to actually prevent that further as well as how to do some validations on build because currently there are no validations at all. But then we go and get the relevant details that we want so just his name and where he was born. The three we that we set. And then just to show that these are in fact just still the default or essentially uninitialized that will print those out as well. So let's get this built. I do want this but not that. And you can see that this does work. It clearly constructed the appropriate thing. Now as I had said numerous times and I cannot possibly make this clear enough please do not ever use this approach in EIDA. It has a lot of problems. It should be obvious that there's a lot of code just used to implement this. That means there's a lot of reasons for bugs. That means you're not using a lot of the native language stuff which means you're not taking advantage of those. You really want to use aggregates because type aggregates are the appropriate way to assign this in EIDA. You can use constructor functions since those essentially just map some stuff onto a aggregate and return the aggregate and that's fine. This approach again should only be done in languages that do not have default parameters. However, because I like challenges and I really don't like telling people things aren't possible because I've been told that a lot when it's been bullshit and I've seen how it can discourage people. Let's get this with sort of the type safety that you'd expect out of EIDA. Let's say that the first and last name absolutely must be defined. The rest of them, we don't really care but you have to have a first and last name. There are some culturalization problems with that. I'm not going to get into it. I'm basing this on the StackOverflow post, how he had it laid out because I wanted to answer the guy. We need to put checks in there. Where in this chain do you think you put the checks? This one. There's two approaches to... I reopened the same exact file. I am a genius. Let's clean this up though. There's two approaches to how to do these checks. I'm going to show the in-code approach first just because I know not everybody is using EIDA 2012 even though I highly recommend you do but I understand design requirements and bureaucracy. Let's show this for you guys. We said first and last name must be defined. So, source first name. These were internally unbounded strings so we're going to have to do this to unbounded string or source last name. Did I seriously... Oh my God, I have been doing so much C sharp. Okay. We need an exception. Let's create an exception real quick. Let's put this down here. Actually no, by convention I usually put them up here. Person... Incomplete. Invalid. Person invalid error. Raise? Yeah. Person invalid error. And I think that's it. So let's try building this. Now this should obviously run fine because we set both first and last name to something other than empty strings. But let's try... I mean let's try setting it to an empty string which should obviously be incorrect since that's what we're comparing it to. And we do get a person invalid error. So let's change this back to segit and let's do fp... fp for failed person because you know we're going to use horrible terminology. Builder and we'll just call build immediately. Okay. So, yeah. You see however though that this isn't a compile time check. This is a run time check. Which is really not the greatest. Plus, at least Nat is telling you where the exception was raised not what line of code caused the exception to be raised. So that's not the greatest for figuring out where your problem was either. Yeah, I'm going to need both of these. So let's remove this because we're going to check for this another way. And... We're going to go to this file and we're going to add in no, not return person with a post. So it's going to be... Ooh, we might run into a problem too. Uh... Can we check this on the result? I'm not sure if we can. We're going to find out though. I'm always down for learning new stuff. First name does not equal to... Or no, wait, these should be calling these so they should just be strings. So let's say invalid prefix and selected component person. Results? Oh yeah, no, because we definitely can't just put person in there. Result? Wait, no, that's through an attribute, I think. Hold Result. So that still didn't check it. I think that's because I'm missing a compiler flag. But let's just try to run this. And yeah, so that obviously should not happen. There's a compiler flag I'm missing and I think it was... If this doesn't work then I'll... Yeah. So it does catch this now. Not as a compile time warning though still. At this... I know there's a way to do this. Don't remember it off the top of my head. So I'm going to cut the video and look up how to actually do this. I think it has to do a spark. I'll be right back. Alright, so as it turns out, I'm not entirely sure how to get this working. I'll be perfectly honest. I really use Spark much. Really, the more complicated projects I do are in C-sharp. I'll be perfectly honest there. I've done some complicated stuff in Ida. I'm sure Spark would be incredibly useful for the containers library and validating that that works correctly. This is something I have every intention of learning soon. I... I don't know how to get this working properly. I've got to play around with that. And when I do, I can get some videos up. But I don't know this right now and I'm not going to mislead you into thinking I do. I know this is the start of it. This is definitely the post-condition you need. And apparently NAT Proof requires a project file. So I got that written. But when I try to run this... NAT Proof against it, I get this and I don't... I don't know what the deal is there. So yeah. Otherwise, I have absolutely shown how the builder pattern works in Ida. I even shown how to do checks against it. I just don't know how to get static checking works working. I'm used to using a different type of code contract. So... Until the next video, have a good one.