2

I have the following interface:

public interface IAgable {
    int Age { get; internal set; }
}

I want the Age property, to be read-only for external assemblies that reference this interface, but also I want the Age property to be set on the interface's same assembly, hence the internal modifier.

This, however, seems to throw a compilation error, as accessibility modifiers may not be used on accessors in an interface.

I want the property to be called from an interface, and I want to be able to set it at an internal level. At the same time, if referenced from an outside project, I want it to be readonly.

Is this possible?

Matias Cicero
  • 25,439
  • 13
  • 82
  • 154
  • 1
    Ommit the set on the interface and put the internal set on the implementation types. – asawyer Nov 14 '14 at 15:30
  • 1
    @asawyer If I take out the `internal set` from the interface, then I have to downcast the interface to its implementation to be able to set the property. I don't want that. – Matias Cicero Nov 14 '14 at 15:30
  • You'll want to use an abstract base type instead of an interface then. – asawyer Nov 14 '14 at 15:31
  • possible duplicate of [C# internal interface with internal implementation](http://stackoverflow.com/questions/6117386/c-sharp-internal-interface-with-internal-implementation) – thumbmunkeys Nov 14 '14 at 15:31
  • @asawyer He doesn't want to provide an implementation, so no. – Servy Nov 14 '14 at 15:32
  • I understand that I'm going against the concept of an interface here. But maybe there is a clean way to accomplish this without using abstract classes – Matias Cicero Nov 14 '14 at 15:33

3 Answers3

8

Have an internal interface that provides both a get and a set, and a public interface that provides only a get. Have the public interface extend the internal interface:

public interface IAgable
{
    int Age { get; }
}

internal interface IAgableInternal : IAgable
{
    int Age { set; }
}
Servy
  • 202,030
  • 26
  • 332
  • 449
4

This is not possible according to Microsoft

Interfaces declared directly within a namespace can be declared as public or internal and, just like classes and structs, interfaces default to internal access. Interface members are always public because the purpose of an interface is to enable other types to access a class or struct. No access modifiers can be applied to interface members.

http://msdn.microsoft.com/en-us/library/ms173121.aspx

Code4U
  • 113
  • 5
0

Try this:

public interface IAgeable {
 MyAge {get;set}
}
public class MyAge:IAgeable{
   public MyAge(int age){
       MyAge = age;
  }
   int MyAge { get; internal set; }
}
JWP
  • 6,672
  • 3
  • 50
  • 74
  • 1
    This does not throw a compilation error if an external assembly tries to set `MyAge` from the interface – Matias Cicero Nov 14 '14 at 15:37
  • The MYAge class is public, it would be included in the assembly and anyone using your interface would have to follow the pattern of creating a new instance by passing in the age parm. (Unless of course they wanted a null object) – JWP Nov 14 '14 at 15:39
  • Won't work in my case because my implementations are internal and hidden from external assemblies. The external assembly just calls a factory for the instance creations. – Matias Cicero Nov 14 '14 at 15:41
  • Then you will have to change your design as the interface by definition will not allow modifiers. You could set up an base class that is inherited instead, as there are no restrictions on that. Or as posted have two interfaces, the problem is that you can never get a private set from an Interface def. – JWP Nov 14 '14 at 15:42
  • You can also set MyAge to private. – JWP Nov 15 '14 at 00:19