Skip to content

Latest commit

 

History

History
253 lines (187 loc) · 6.9 KB

UPGRADING_TO_v2.x.md

File metadata and controls

253 lines (187 loc) · 6.9 KB

Upgrading to 2.x

Overview

The approach taken in v2.0 of this addon has changed drastically from versions <= v1.0 and will require some modifications to config and code in order to upgrade. The steps below outline the things you will need to change in order to upgrade to v2.0.

Migrate config

Mirgate config from this:

// config/environment.js

module.exports = function (environment) {
  let ENV = {
    launchDarkly: {
      clientSideId: '1234',
      local: true,
      localFeatureFlags: {
        foo: true,
      },
      streaming: {
        foo: true,
      },
    },
  };
};

to this:

module.exports = function (environment) {
  let ENV = {
    launchDarkly: {
      clientSideId: '1234',
      mode: 'local',
      localFlags: {
        foo: true,
      },
      streamingFlags: {
        foo: true,
      },
    },
  };
};

Migrate this.launchDarkly.initialize

Ember Launch Darkly no longer uses services and so the initialization should change from this:

// /app/routes/application.js

import Route from '@ember/routing/route';

export default Route.extend({
  model() {
    let user = {
      key: 'aa0ceb',
      anonymous: true,
    };

    return this.launchDarkly.initialize(user);
  },
});

to this:

// /app/routes/application.js

import Route from '@ember/routing/route';

import config from 'my-app/config/environment';

import { initialize } from 'ember-launch-darkly';

export default class ApplicationRoute extends Route {
  async model() {
    let user = {
      key: 'aa0ceb',
    };

    let { clientSideId, ...rest } = config;
    
    return await initialize(clientSideId, user, rest);
  }
}

Migrate this.launchDarkly.identify

Ember Launch Darkly no longer uses services and so the identification should change from this:

// /app/routes/session.js

import Route from '@ember/routing/route';

export default Route.extend({
  session: service(),

  model() {
    return this.session.getSession();
  },

  afterModel(session) {
    let user = {
      key: session.get('user.id'),
      firstName: session.get('user.firstName'),
      email: session.get('user.email'),
    };

    return this.launchDarkly.identify(user);
  },
});

to this:

// /app/routes/session.js

import Route from '@ember/routing/route';
import { inject as service } from '@ember/service';

import { identify } from 'ember-launch-darkly';

export default class SessionRoute extends Route {
  @service session;

  model() {
    return this.session.getSession();
  },

  async afterModel(session) {
    let user = {
      key: session.user.id,
      firstName: session.user.firstName,
      email: session.user.email
    };

    return await identify(user);
  }
}

Migrate this.launchDarkly.variation

Ember Launch Darkly no longer uses services and so checking of variations should change from this:

// /app/components/login-page/component.js

import Component from '@ember/component';
import { computed } from '@ember/object';

export default Component.extend({
  actions: {
    getPrice() {
      if (this.launchDarkly.variation('new-price-plan')) {
        return 99.0;
      }

      return 199.0;
    },
  },
});

to this:

// /app/components/login-page/component.js

import Component from '@ember/component';

import { variation } from 'ember-launch-darkly';

export default class LoginPageComponent extends Component {
  get price() {
    if (variation('new-price-plan')) {
      return 99.0;
    }

    return 199.0;
  }
}

A note on the experimental variation Javascript helper

Versions of this addon pre v2.0 included an experimental Babel transform that allowed users to import a variation function in to Javascript instead of referencing this.launchDarkly.variation. It was more than a shorthand for the variation function - it also tried to be a bit clever and, when used inside a computed property, attempted to add the feature flags as dependent keys of the computed property so as to ensure the computed property was re-computed if the flag changed.

While this helper was useful, it was infinitely problematic. Thankfully, in an Ember Octane world, or more specifically, an @tracked world, this is totally unnecessary. Any code that checks for feature flags will re-compute if the flag changes based on the fact that the flags are now tracked in v2.0.

Because the import of the variation function in v2.0 is the same as the import of the old babel transform helper, no changes should need to be made here.

However, if you are using v1.0.0 specifically, there are likely a couple of changes you will need to make.

No doubt you will have stopped using the computedWithVariation helper (DOC) as you won't be using computed properties in Octane any more and it doesn't work with the @computed decorator.

However, you should also remove the code in your ember-cli-build.js that enables the Babel transform. So, remove this:

// ember-cli-build.js

const EmberApp = require('ember-cli/lib/broccoli/ember-app');

module.exports = function (defaults) {
  let app = new EmberApp(defaults, {
    babel: {
      plugins: [require.resolve('ember-launch-darkly/babel-plugin')], // <---- Remove this plugin.
    },
  });

  return app.toTree();
};

Accessing local feature flags from the JS console

If you want to access and modify local feature flags from the JS console you will need to change from doing this:

ld.variation('new-pricing-plan', 'plan-a'); // return the current value of the feature flag providing a default if it doesn't exist
ld.setVariation('new-pricing-plan', 'plan-x'); // set the variation value
ld.enable('apply-discount'); // helper to set the return value to `true`
ld.disable('apply-discount'); // helper to set the return value to `false`
ld.allFlags(); // return the current list of feature flags and their values
ld.user();

to this:

> window.__LD__.get('new-pricing-plan', 'plan-a') // return the current value of the feature flag providing a default ('plan-a' if it doesn't exist (the default is optional)
> window.__LD__.set('new-pricing-plan', 'plan-x') // set the variation value
> window.__LD__.enable('apply-discount') // helper to set the return value to `true`
> window.__LD__.disable('apply-discount') // helper to set the return value to `false`
> window.__LD__.allFlags // return the current list of feature flags and their values
> window.__LD__.user // return the user that the client has been initialized with