Skip to content

Instantly share code, notes, and snippets.

@tchardin
Last active April 17, 2020 20:09
Show Gist options
  • Save tchardin/cb158662bf229ba5a69ccd1bc9a8c4e9 to your computer and use it in GitHub Desktop.
Save tchardin/cb158662bf229ba5a69ccd1bc9a8c4e9 to your computer and use it in GitHub Desktop.
Generated by XState Viz: https://xstate.js.org/viz
const CHART = 'cic';
const HISTORY = 'backToPrevStep';
// states
const LIFE_CHANGE_INTRO = 'lifeChangeIntro';
const MANAGE_COVERAGE_INTRO = 'manageCoverageIntro';
const ADD_MEMBER_REASON = 'addMemberReason';
const REMOVE_MEMBER_REASON = 'removeMemberReason';
const CHANGE_SELECTION = 'changeSelection';
const ADDRESS_ENTRY = 'addressEntry';
const ADDRESS_NO_CHANGE = 'addressNoChange';
const INCOME_ENTRY = 'incomeEntry';
const BASICS_ENTRY = 'basicsEntry';
const INCOME_NO_CHANGE = 'incomeNoChange';
const GOV_HANDOFF = 'govHandoff';
const GOV_PICKUP = 'govPickup';
const STATE_HANDOFF = 'stateHandoff';
const STATE_PICKUP = 'statePickup';
const APP_REVIEW_INTRO = 'appReviewIntro';
const MEMBER_MARRIAGE = 'memberMarriage';
const DIVORCE_INTRO = 'divorceIntro';
const DEATH_INTRO = 'deathIntro';
const CUSTODY_INTRO = 'custodyIntro';
const COVERAGE_OPTIONS_INTRO = 'coverageOptionsIntro';
const POLICY_CANCEL_PROMPT = 'policyCancelPrompt';
const MOVE_DATE_ENTRY = 'moveDateEntry';
const MEMBER_DIVORCE = 'memberDivorce';
const MEMBER_DEATH = 'memberDeath';
const NEW_PLAN_INTRO = 'newPlanIntro';
const MEMBER_CUSTODY = 'memberCustody';
const MEMBER_JOB_COVERAGE = 'memberJobCoverage';
const MEMBER_COVERAGE_LOSS = 'memberCoverageLoss';
const MEMBER_FUTURE_COVERAGE_LOSS = 'memberFutureCoverageLoss';
const MEMBER_STATUS_CHANGE = 'memberStatusChange';
const SEP_OUTDATED = 'sepOutdated';
const REMOVING_MEMBERS = 'removingMembers';
const SEP_MOVE_OUTDATED = 'sepMoveOutdated';
const SEP_MOVE_OUTDATED_POLICY_VALID = 'sepMoveOutdatedPolicyValid';
const POLICY_INVALID = 'policyInvalid';
const SEP_KEEP_OR_APPLY = 'sepKeepOrApply';
const SEP_MUST_APPLY = 'sepMustApply';
const FINANCIAL_ASSISTANCE = 'financialAssistance';
const MEMBER_CUT = 'memberCut';
// enrollment flow
const ENROLLMENT_FLOW = '/health/household';
const INCOME_FLOW = '/health/member-income-list';
const PLAN_DETAIL = 'planDetail';
// events
const START = 'START';
const APPROVE = 'APPROVE';
const DISMISS = 'DISMISS';
const SUBMIT = 'SUBMIT';
const DONE = 'DONE';
const NEXT = 'NEXT';
const OPEN_URL = 'OPEN_URL';
const CANCEL_POLICY = 'CANCEL_POLICY';
const APPLY = 'APPLY';
// Combine multiple guards while keeping a
// proper key for debugging
const applyAny = (ctx, event, { guard }) => {
const gList = guard.guards.split('|');
return gList.some(guardKey => guards[guardKey](ctx, event));
};
const applyEvery = (ctx, event, { guard }) => {
const gList = guard.guards.split('&');
return gList.every(guardKey => guards[guardKey](ctx, event));
};
// conditions
const guards = {
incomeChanged: (ctx, evt) => {
return evt.change === 'INCOME';
},
addressChanged: (ctx, evt) => {
return evt.change === 'ADDRESS';
},
gotPregnant: (ctx, evt) => {
return evt.change === 'PREGNANCY';
},
memberMarried: (ctx, evt) => {
return evt.change === 'MARRIAGE';
},
isBirth: (ctx, evt) => {
return evt.change === 'BIRTH';
},
isAdoption: (ctx, evt) => {
return evt.change === 'ADOPTION';
},
childTurned26: (ctx, evt) => {
return evt.change === 'CHILD_26';
},
isDivorce: (ctx, evt) => {
return evt.change === 'DIVORCE';
},
isDeath: (ctx, evt) => {
return evt.change === 'DEATH';
},
coverageChanged: (ctx, evt) => {
return evt.change === 'COVERAGE';
},
custodyChanged: (ctx, evt) => {
return evt.change === 'CUSTODY';
},
offeredJobCoverage: (ctx, evt) => {
return evt.change === 'COVERAGE_GAIN_JOB';
},
gainedCoverage: (ctx, evt) => {
return evt.change === 'COVERAGE_GAIN';
},
lostCoverage: (ctx, evt) => {
return evt.change === 'COVERAGE_LOSS';
},
willLoseCoverage: (ctx, evt) => {
return evt.change === 'FUTURE_COVERAGE_LOSS';
},
filingStatusChanged: (ctx, evt) => {
return evt.change === 'FILING_STATUS';
},
citizenshipChanged: (ctx, evt) => {
return evt.change === 'CITIZENSHIP';
},
incarcerationChanged: (ctx, evt) => {
return evt.change === 'INCARCERATION';
},
tribeMembershipChanged: (ctx, evt) => {
return evt.change === 'TRIBE_MEMBERSHIP';
},
disabilityChanged: (ctx, evt) => {
return evt.change === 'DISABILITY';
},
legalNameChanged: (ctx, evt) => {
return evt.change === 'LEGAL_NAME';
},
dobChanged: (ctx, evt) => {
return evt.change === 'DOB';
},
ssnChanged: (ctx, evt) => {
return evt.change === 'SSN';
},
isAddMember: (ctx, evt) => {
return evt.change === 'ADD_MEMBER';
},
isRemoveMember: (ctx, evt) => {
return evt.change === 'REMOVE_MEMBER';
},
isCancelPolicy: (ctx, evt) => {
return evt.change === 'CANCEL_POLICY';
},
isOther: (ctx, evt) => {
return evt.change === 'OTHER';
},
'isBirth|isAdoption|disabilityChanged': applyAny,
'childTurned26|isDivorce|isDeath|custodyChanged': applyAny,
'filingStatusChanged|citizenshipChanged|incarcerationChanged|tribeMembershipChanged': applyAny,
'legalNameChanged|ssnChanged|dobChanged': applyAny,
'citizenshipChanged|incarcerationChanged': applyAny,
'childTurned26|isOther': applyAny,
'gainedCoverage|disabilityChanged': applyAny,
'filingStatusChanged|incarcerationChanged': applyAny,
// household basics conditions WIP
updatedTaxHousehold: (ctx, evt) => {
return evt.dirty;
},
prelimEligUnchanged: (ctx, evt) => {
// TODO compare all results with current app
return false;
},
// Location change
'movedToFedMarketplace|movedCurrentPolicyValid|movedCurrentPolicyInvalid': applyAny,
movedToStateMarketplace: (ctx, evt) => {
return false;
},
movedParamsUnchanged: (ctx, evt) => {
// TODO: backend feat
return false;
},
isWithin60Days: (ctx, evt) => {
return true;
},
isWithinNext60Days: (ctx, evt) => {
return true;
},
isPolicyValid: (ctx, evt) => {
return evt.policyValid;
},
'isWithin60Days&isPolicyValid': applyEvery,
'isWithin60Days&isPolicyInvalid': applyEvery,
isPolicyInvalid: (ctx, evt) => {
return !evt.policyValid;
},
isFiler: (ctx, evt) => {
return evt.relation === 'SELF';
},
isSpouse: (ctx, evt) => {
return evt.relation === 'SPOUSE';
},
isMultiMembers: (ctx, evt) => {
return evt.members?.length > 1;
},
isFilerOrSpouse: (ctx, evt) => {
return evt.relation === 'SELF' || evt.relation === 'SPOUSE';
},
isOtherRelative: (ctx, evt) => {
return evt.relation !== 'SELF' && evt.relation !== 'SPOUSE';
},
gotDMI: (ctx, evt) => {
return evt.dmis && evt.dmis.length > 0;
},
shouldKeepMember: (ctx, evt) => {
return evt.relation !== 'SELF' && !evt.removeMember;
},
'isFiler&isMultiMembers': applyEvery,
'isFilerOrSpouse|shouldKeepMember': applyAny,
};
const combine = type => ({
type,
guards: type,
});
const chart = Machine({
id: CHART,
initial: LIFE_CHANGE_INTRO,
context: {},
states: {
[LIFE_CHANGE_INTRO]: {
on: {
[START]: CHANGE_SELECTION,
},
},
[MANAGE_COVERAGE_INTRO]: {
on: {
[SUBMIT]: [
{ target: ADD_MEMBER_REASON, cond: 'isAddMember' },
{ target: REMOVE_MEMBER_REASON, cond: 'isRemoveMember' },
{ target: POLICY_CANCEL_PROMPT, cond: 'isCancelPolicy' },
{ target: ENROLLMENT_FLOW },
],
},
},
[CHANGE_SELECTION]: {
on: {
[SUBMIT]: [
{
target: BASICS_ENTRY,
cond: 'incomeChanged',
},
{
target: APP_REVIEW_INTRO,
cond: combine('isBirth|isAdoption|disabilityChanged'),
},
{ target: ADDRESS_ENTRY, cond: 'addressChanged' },
{ target: MEMBER_MARRIAGE, cond: 'memberMarried' },
{ target: GOV_HANDOFF, cond: 'gotPregnant' },
{
target: DIVORCE_INTRO,
cond: 'isDivorce',
},
{ target: DEATH_INTRO, cond: 'isDeath' },
{ target: CUSTODY_INTRO, cond: 'custodyChanged' },
{ target: COVERAGE_OPTIONS_INTRO, cond: 'coverageChanged' },
{
target: MEMBER_STATUS_CHANGE,
cond: combine(
'filingStatusChanged|citizenshipChanged|incarcerationChanged|tribeMembershipChanged',
),
},
],
},
},
[BASICS_ENTRY]: {
on: {
[SUBMIT]: [
{ target: APP_REVIEW_INTRO, cond: 'updatedTaxHousehold' },
{ target: INCOME_ENTRY },
],
},
},
[INCOME_ENTRY]: {
on: {
[SUBMIT]: [
{ target: INCOME_NO_CHANGE, cond: 'prelimEligUnchanged' },
{
target: FINANCIAL_ASSISTANCE,
},
],
[APPLY]: ENROLLMENT_FLOW,
},
},
[INCOME_NO_CHANGE]: {
on: {
[DONE]: PLAN_DETAIL,
[APPLY]: ENROLLMENT_FLOW,
},
},
[APP_REVIEW_INTRO]: {
on: {
[NEXT]: ENROLLMENT_FLOW,
[DISMISS]: PLAN_DETAIL,
},
},
[DIVORCE_INTRO]: {
on: {
[NEXT]: MEMBER_DIVORCE,
},
},
[MEMBER_DIVORCE]: {
on: {
[SUBMIT]: [
{ target: GOV_HANDOFF, cond: 'isOtherRelative' },
{ target: REMOVING_MEMBERS, cond: 'isSpouse' },
{ target: APP_REVIEW_INTRO },
],
},
},
[DEATH_INTRO]: {
on: {
[NEXT]: MEMBER_DEATH,
},
},
[MEMBER_DEATH]: {
on: {
[SUBMIT]: [
{ target: NEW_PLAN_INTRO, cond: combine('isFiler&isMultiMembers') },
{ target: POLICY_CANCEL_PROMPT, cond: 'isFiler' },
{ target: REMOVING_MEMBERS },
],
},
},
[CUSTODY_INTRO]: {
on: {
[NEXT]: MEMBER_CUSTODY,
},
},
[MEMBER_CUSTODY]: {
on: {
[SUBMIT]: [
{ target: GOV_HANDOFF, cond: 'shouldKeepMember' },
{ target: REMOVING_MEMBERS },
],
},
},
[COVERAGE_OPTIONS_INTRO]: {
on: {
[SUBMIT]: [
{ target: MEMBER_JOB_COVERAGE, cond: 'offeredJobCoverage' },
{ target: APP_REVIEW_INTRO, cond: 'gainedCoverage' },
{ target: MEMBER_COVERAGE_LOSS, cond: 'lostCoverage' },
{ target: MEMBER_FUTURE_COVERAGE_LOSS, cond: 'willLoseCoverage' },
],
},
},
[ADDRESS_ENTRY]: {
on: {
[SUBMIT]: [
{ target: ADDRESS_NO_CHANGE, cond: 'movedParamsUnchanged' },
{ target: STATE_HANDOFF, cond: 'movedToStateMarketplace' },
{
target: MOVE_DATE_ENTRY,
},
],
},
},
[MOVE_DATE_ENTRY]: {
on: {
[SUBMIT]: [
{
target: SEP_KEEP_OR_APPLY,
cond: combine('isWithin60Days&isPolicyValid'),
},
{
target: SEP_MUST_APPLY,
cond: combine('isWithin60Days&isPolicyInvalid'),
},
{
target: SEP_MOVE_OUTDATED_POLICY_VALID,
cond: 'isPolicyValid',
},
{
target: SEP_MOVE_OUTDATED,
},
],
},
},
[STATE_HANDOFF]: {
on: {
[OPEN_URL]: STATE_PICKUP,
},
},
[STATE_PICKUP]: {
on: {
[DONE]: PLAN_DETAIL,
[CANCEL_POLICY]: POLICY_CANCEL_PROMPT,
},
},
[POLICY_CANCEL_PROMPT]: {
on: {
[DISMISS]: HISTORY,
},
},
[ADDRESS_NO_CHANGE]: {
on: {
[DONE]: PLAN_DETAIL,
},
},
[SEP_MOVE_OUTDATED]: {
on: {
[NEXT]: POLICY_INVALID,
[APPLY]: ENROLLMENT_FLOW,
},
},
[SEP_OUTDATED]: {
on: {},
},
[POLICY_INVALID]: {
on: {
[CANCEL_POLICY]: POLICY_CANCEL_PROMPT,
[DISMISS]: PLAN_DETAIL,
},
},
[SEP_KEEP_OR_APPLY]: {
on: {
[APPLY]: ENROLLMENT_FLOW,
[DISMISS]: PLAN_DETAIL,
},
},
[SEP_MUST_APPLY]: {
on: {
[DISMISS]: PLAN_DETAIL,
[APPLY]: ENROLLMENT_FLOW,
},
},
[SEP_MOVE_OUTDATED_POLICY_VALID]: {
on: {
[DONE]: PLAN_DETAIL,
[APPLY]: ENROLLMENT_FLOW,
},
},
[GOV_HANDOFF]: {
on: {
[OPEN_URL]: GOV_PICKUP,
},
},
[GOV_PICKUP]: {
on: {
[DONE]: PLAN_DETAIL,
},
},
[MEMBER_MARRIAGE]: {
on: {
[SUBMIT]: [
{ target: GOV_HANDOFF, cond: 'shouldKeepMember' },
{ target: APP_REVIEW_INTRO, cond: 'isFiler' },
{ target: REMOVING_MEMBERS },
],
},
},
[MEMBER_JOB_COVERAGE]: {
on: {
[SUBMIT]: [
{
target: GOV_HANDOFF,
cond: combine('isFilerOrSpouse|shouldKeepMember'),
},
{ target: REMOVING_MEMBERS },
],
},
},
[MEMBER_COVERAGE_LOSS]: {
on: {
[SUBMIT]: [
{ target: APP_REVIEW_INTRO, cond: 'isWithin60Days' },
{ target: SEP_OUTDATED },
],
},
},
[MEMBER_FUTURE_COVERAGE_LOSS]: {
on: {
[SUBMIT]: [
{ target: APP_REVIEW_INTRO, cond: 'isWithinNext60Days' },
{ target: SEP_OUTDATED },
],
},
},
[MEMBER_STATUS_CHANGE]: {
on: {
[SUBMIT]: [
{ target: APP_REVIEW_INTRO, cond: 'isWithin60Days' },
{ target: GOV_HANDOFF, cond: 'isNotPhase1' },
{ target: SEP_OUTDATED },
],
},
},
[REMOVING_MEMBERS]: {
on: {
[DONE]: APP_REVIEW_INTRO,
},
},
[FINANCIAL_ASSISTANCE]: {
on: {
[NEXT]: INCOME_FLOW,
},
},
[NEW_PLAN_INTRO]: {
on: {
[NEXT]: ENROLLMENT_FLOW,
},
},
[ADD_MEMBER_REASON]: {
on: {
[SUBMIT]: [
{
target: APP_REVIEW_INTRO,
cond: combine('isBirth|isAdoption|disabilityChanged'),
},
{
target: MEMBER_STATUS_CHANGE,
cond: combine('citizenshipChanged|incarcerationChanged'),
},
{ target: MEMBER_COVERAGE_LOSS, cond: 'lostCoverage' },
{ target: MEMBER_MARRIAGE, cond: 'memberMarried' },
],
},
},
[REMOVE_MEMBER_REASON]: {
on: {
[SUBMIT]: [
{ target: MEMBER_CUT, cond: combine('childTurned26|isOther') },
{ target: MEMBER_JOB_COVERAGE, cond: 'offeredJobCoverage' },
{
target: APP_REVIEW_INTRO,
cond: combine('gainedCoverage|disabilityChanged'),
},
{
target: DIVORCE_INTRO,
cond: 'isDivorce',
},
{ target: DEATH_INTRO, cond: 'isDeath' },
{ target: CUSTODY_INTRO, cond: 'custodyChanged' },
{
target: MEMBER_STATUS_CHANGE,
cond: combine('filingStatusChanged|incarcerationChanged'),
},
],
},
},
[MEMBER_CUT]: {
on: {
[SUBMIT]: [
{ target: GOV_HANDOFF, cond: 'shouldKeepMember' },
{ target: REMOVING_MEMBERS },
],
},
},
[INCOME_FLOW]: {
type: 'redirect',
},
[ENROLLMENT_FLOW]: {
type: 'redirect',
},
[PLAN_DETAIL]: {
type: 'exit',
},
[HISTORY]: {
type: 'history',
},
},
},
{
guards,
})
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment