Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Restrict types that may implement a Trait

Tags:

oop

groovy

traits

Is it possible to restrict the types that can implement a trait? Say, for example I have a type

interface Something {
  void foo() 
}

and a trait

trait SomethingAbility {
  void bar()  {
    println "bar"
  }
}

Is there a way that I can only allow the trait to be implemented by classes that are of type Something, e.g.

// OK
class SomethingImpl implements Something, SomethingAbility {
  void foo() {
    println "foo"
  }
}

// error: this class should not be allowed to implement the trait
// because it's not a Something
class NotSomething implements SomethingAbility {
  void foo() {
    println "foo"
  }
}

One option is to add an abstract method to the trait

trait SomethingAbility {
  void bar() {
    println "bar"
  }

  abstract void foo()
}

This will mean that the trait can't be implemented by a class unless that class also provides a foo() method, but this isn't the same thing as the class being of type Something

like image 825
Dónal Avatar asked Mar 27 '15 10:03

Dónal


1 Answers

I think what you are looking for is @Selftype, see http://docs.groovy-lang.org/docs/latest/html/gapi/groovy/transform/SelfType.html Basically it states what a class using this trait has to implement. So with

@SelfType(Something)
trait SomethingAbility {
   void bar()  {
     println "bar"
   }
}

you declare, that any class using this trait will also have to implement the interface Something. This ensures for example, that if you statically compile the trait and you call a method from the interface Something, that compilation will not fail. of course for standard Groovy this is not required, because of duck typing.

like image 123
blackdrag Avatar answered Oct 08 '22 13:10

blackdrag