1

Background: I have a large application that imports entities from one system into another. The source system has a primary key, which I'll call SourceId, and the destination system has its own key, which I'll call DestinationId, but the destination record also records the SourceId property, so a destination record can be used to find the source record.

Suppose I have code like this:

    Class Destination
      Public DestinationId As String
      Public SourceId As String
    End Class

    Dim src = GetSource()
    Dim dst = New Destination();
    
    dst.DestinationId = RandomGuidString()
    dst.SourceId = src.Id

Because both Id properties are strings with similar names, it's easy to mix them up:

    dst.DestinationId = src.Id   <---BUG! I meant to set dst.SourceId instead

What I'd really like is the ability to do this:

    TypeAlias SourceId = System.String
    TypeAlias DestinationId = System.String

    Class Destination
      Public DestinationId As DestinationId
      Public SourceId As SourceId
    End Class

   
    dst.DestinationId = src.Id   <---Now this causes a compiler error because the types are different, even though they're really both strings

So is there any way in .NET to define a type alias for primitive types that the compiler can enforce in this way.

This is VB.NET, but I'm curious about c# as well.

Joshua Frank
  • 13,120
  • 11
  • 46
  • 95
  • What's your thoughts about using an implicit conversion? – Trevor Feb 25 '21 at 17:41
  • "Public DestinationId As DestinationId" is a type so you need a property : Try dst.DestinationId.xyz (xyz you need to change to an actual property). – jdweng Feb 25 '21 at 17:42
  • @Codexer: I'm good with implicit conversions. What's your idea? – Joshua Frank Feb 25 '21 at 17:43
  • Is the straightforward approach of two identical but unrelated classes that both can be constructed from string not good enough? – GSerg Feb 25 '21 at 17:49
  • @GSerg: How would that work, including being transparently serializable as strings in, say, JSON? – Joshua Frank Feb 25 '21 at 17:55
  • You can alias types, but if `DestinationId` and `SourceId` both alias `System.String`, then it won't solve the problem. I just means that now there are three "types" that can be assigned to `DestinationId` instead of one. I think you'd have to actually change the types to something else, like an `enum` or custom class. – Rufus L Feb 25 '21 at 18:30
  • `Imports DestinationId = System.String` in VB.net or `using DestinationId = System.String` in C# – Rufus L Feb 25 '21 at 18:34
  • @RufusL: As you say, you can do this, but since they're all strings, the compiler won't flag an assignment from one to the other, which is what I'm trying to accomplish. – Joshua Frank Feb 25 '21 at 19:13
  • @JoshuaFrank Just a class with a constructor that accepts a string, and a property called, say, `Value`, that is decorated with attributes from your respective json library. E.g. for newtonsoft json, see https://stackoverflow.com/q/24472404/11683 for serializing a class to a single value (and back). – GSerg Feb 25 '21 at 19:37
  • Either you are overthinking this or we don't have the full story. Why not just write a factory method that returns a new `Destination` instance that takes a source type as its argument? That way you write and verify that the factory method is correct and you no longer need to hard code the property transfers each time. – TnTinMn Feb 25 '21 at 19:49
  • @TnTinMn: If I'm understanding you, because I want to be able to say `obj.SourceId = src.Id`, not something more cumbersome like `obj.SourceId = SourceIdFactory.FromId(src.Id)` – Joshua Frank Feb 25 '21 at 19:54
  • What I meant is that the factory method contains the code statements to copy from the Source fields to the Destination fields. You only write this method once and test that it works correctly. Your question implies that you have the field copying code repeated many times and you are looking for a way to have the compiler tell you that a logic fault exists on any given transcription statement. That is not the compiler's job. Your code can have many logic faults that are syntax correct but do not do what is wanted/needed. – TnTinMn Feb 25 '21 at 20:10
  • 1
    @TnTinMn: That's not really what I'm saying. It's not that I copy the fields from source to destination a lot, it's that I have a lot of complex code for associating different objects and it's not too hard to use a `SourceId` by mistake when I intend to use a `DestinationId`. What I *want* is for these to be different data types precisely so that the compiler catches such a mistake, even though the fields are in fact both strings. – Joshua Frank Feb 25 '21 at 20:19

0 Answers0