Loopback-next: Fix and document `MixinBuilder`

Created on 25 Oct 2017  ·  12Comments  ·  Source: strongloop/loopback-next

Problem:

The problem of MixinBuilder from my test is: function with() doesn't set its returned type as a class extends the BaseClass:
click to see test example

let AppWithRepoMixin = class extends MixinBuilder.mix(Application).with(RepositoryMixin){};

const myApp = new AppWithRepoMixin();
const boundComponentsBefore = myApp.find('components.*').map(b => b.key);

fails when compiling, because compiler doesn't know myApp is an instance of Application, therefore doesn't know it has a prototype function find() returning an Array. The code calls map with any instead of Array and fails.

This looks like a stop for people wanting to use it...

I am going to defer writing doc for MixinBuilder and create an issue for it. I still love the fluent api and would like to dig more :star:

Document cut from PR https://github.com/strongloop/loopback.io/pull/491

Mixin Builder

LoopBack provides a mixin builder function MixinBuilder to easily extend a class
with one or multiple mixins,
you can call it to define the new extended class with fluent syntaxed API like:

import {MixiBuilder} from '@loopback/repository';
import {BaseClass} from '<path_exports_BaseClass>';
import {FooMixin, BarMixin} from '<path_exports_Mixins>';

let newClass = MixinBuilder.mix(baseClass).with(FooMixin, BarMixin);

Acceptance Criteria

  • [ ] Move MixinBuilder class from @loopback/repository to @loopback/core
  • [ ] Fix MixinBuilder to return the correct type for class as it currently fails to do so
  • [ ] Update TSDocs for this Class
  • [ ] Tests

  • _Bonus: See if this can be just a static method on Application instead of a new Class as proposed here: https://github.com/strongloop/loopback-next/issues/673#issuecomment-374252583 DO NOT SPEND MORE THAN 1 HOUR on this. Fixing the class is good enough for this task._

bug team-apex

Most helpful comment

+1 for fixing it. I would also like to see this moved from @loopback/repository to @loopback/core since we are mixing in to the Application class most of the times.

I'd also like to see if we can possibly change the behaviour of MixinBuilder to remove the MixinBuilder class entirely and have something like class MyApp extends Application.with(Mixin1, Mixin2, ...). Reference to something similar we were considering adding: https://github.com/strongloop/loopback-next/pull/824/commits/cb03b8f8d270713bec6f32416b36ced15f84eeae

This would simplify the normal way of Mixins (remove the requirement of adding tedious brackets and makes it easier to use imo). with can be withMixins.

If we agree on this approach, we should update our code / tests / docs to use this approach and make this our recommended approach for Mixins.

All 12 comments

+1 for fixing it. I would also like to see this moved from @loopback/repository to @loopback/core since we are mixing in to the Application class most of the times.

I'd also like to see if we can possibly change the behaviour of MixinBuilder to remove the MixinBuilder class entirely and have something like class MyApp extends Application.with(Mixin1, Mixin2, ...). Reference to something similar we were considering adding: https://github.com/strongloop/loopback-next/pull/824/commits/cb03b8f8d270713bec6f32416b36ced15f84eeae

This would simplify the normal way of Mixins (remove the requirement of adding tedious brackets and makes it easier to use imo). with can be withMixins.

If we agree on this approach, we should update our code / tests / docs to use this approach and make this our recommended approach for Mixins.

+1 for everything @virkt25 said

I was never a fan of MixinBuilder. I am happy with both proposals: fix it or remove it. 👍

+1 to @virkt25's proposal as well. I'm okay to remove it until we fix it :-).

I have been tried different strategies in PR https://github.com/strongloop/loopback-next/pull/1305 to "Fix MixinBuilder to return the correct type for class", but there is no easy way to do it.
And the mixin-builder.ts file(and common-types.ts) should be moved into a new util package instead of the core package. The new util package will be a place for language related util functions/interfaces/types.

@dhmlau @shimks Since the mixin builder is a sugar function, users can apply mixins in the chain signature, shall we drop this story from DP3 and revisit it when have more bandwidth?

Hmm, just took a quick look of the task https://github.com/strongloop/loopback-next/issues/1171, if we can define and apply the mixin in the class signature instead of the function, that could potentially solve both two issues....Let me give it a last try!

@dhmlau @shimks Since the mixin builder is a sugar function, users can apply mixins in the chain signature, shall we drop this story from DP3 and revisit it when have more bandwidth?

I agree. It was not the original intention to spend too much effort for the sugar functions anyway.
What do you think @bajtos @raymondfeng ?

@dhmlau There seems no easy way to get the class signature work either...shall we defer to work on it after DP3?

We can get back to it whenever we are confident that there is a feasible solution to apply multiple mixins with a sugar function.
From my investigation, there isn’t one working yet…

If we need more research, then I am proposing to defer the work after DP3.

Personally, I still think we should remove MixinBuilder completely from our code base and docs. If we agree on this direction, then I think it makes sense to make that happen in DP3, probably as a p2 task.

I'm ok with removing MixinBuilder. I'm also ok with fixing it, but from what I've seen with work that went to attempting to create a PR for this task, coming up a solution seems like a real headache.

Seems like we have some consensus.. removing this from DP3

On a second thought, shall we close this task (because we're not fixing it) and create a new one to remove MixinBuilder and mark it as DP3 p2?

Was this page helpful?
0 / 5 - 0 ratings