Skip to content

Instantly share code, notes, and snippets.

@petsel
Created February 14, 2017 12:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save petsel/e14efdf5a0d8670b2763bcaf2275bc97 to your computer and use it in GitHub Desktop.
Save petsel/e14efdf5a0d8670b2763bcaf2275bc97 to your computer and use it in GitHub Desktop.
example pseudo code featuring a possible next generation ECMAScript Trait Syntax
trait customTrait {
use { Trait_A, Trait_B, Trait_C }
apply all
apply all without { methodName_z, methodName_y }
apply { Trait_A }
apply { Trait_A, Trait_C } without { methodName_x }
apply { Trait_A:bigTalk } // - this is the equivalent to Scala's 'override'
// or to PHP's 'insteadof'.
apply { Trait_B:bigTalk } as { talk } // - aliasing
//alias { Trait_B:bigTalk } as { talk } // - aliasing too ... just another possible wording.
apply { Trait_B:initialize } before { Trait_C } // - 'before' and 'after' do composes the equally named
// behavior of two traits into one behavior whilst
// preserving theirs specified processing precedence.
//apply { Trait_C:initialize } after { Trait_A }
//apply { Trait_B:initialize } before { Trait_C } after { Trait_A } before { Trait_A } after { Trait_C }
applicator(/* payload for stateful traits */) {
this.sanitize = function () { /* ... */ };
// - the applicator is the place for implementing all of a
// trait's specific behavior that is not covered by or is
// supposed to overrule the trait composition results of
// 'use { ... } apply { ... }'.
//
// - statefull traits easily can be achieved by passing
// additional state into the applicable object via 'call'
// or 'apply', thus passing it into the 'applicator's
// arguments array.
}
before initialize() {
this.sanitize(); // invokes the applicator's 'sanitize' before 'initialize' will be processed.
// - the 'before' modifier just changes the precedence
// of how two methods will be processed. Its provided
// callback always will be invoked before the original
// control flow proceeds.
}
before methodName() {
// - each method modifications will be accumulated and nested / wrapped.
}
after validate(returnValue, argsArray) {
// - the 'after' modifier always accesses the arguments and
// the result of the method that has been processed before
// and passes both to its provided callback as <returnValue>
// and <argsArray>.
}
around ["non valid method identifier"](intercepted, intercepting, argsArray) {
// - the 'around' modifier always does access not only the
// arguments array but also both methods that are going
// to be processed, the intercepted one and its provided
// callback that in this case is the interceptor itself.
// Arguments and both methods then get passed into the
// intercepting callback.
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment