@@ -1490,105 +1490,16 @@ export default class Optimizely implements Client {
1490
1490
}
1491
1491
1492
1492
decide ( user : OptimizelyUserContext , key : string , options : OptimizelyDecideOption [ ] = [ ] ) : OptimizelyDecision {
1493
- const userId = user . getUserId ( ) ;
1494
- const attributes = user . getAttributes ( ) ;
1495
1493
const configObj = this . projectConfigManager . getConfig ( ) ;
1496
- const reasons : ( string | number ) [ ] [ ] = [ ] ;
1497
- let decisionObj : DecisionObj ;
1494
+
1498
1495
if ( ! this . isValidInstance ( ) || ! configObj ) {
1499
1496
this . logger . log ( LOG_LEVEL . INFO , LOG_MESSAGES . INVALID_OBJECT , MODULE_NAME , 'decide' ) ;
1500
1497
return newErrorDecision ( key , user , [ DECISION_MESSAGES . SDK_NOT_READY ] ) ;
1501
1498
}
1502
1499
1503
- const feature = configObj . featureKeyMap [ key ] ;
1504
- if ( ! feature ) {
1505
- this . logger . log ( LOG_LEVEL . ERROR , ERROR_MESSAGES . FEATURE_NOT_IN_DATAFILE , MODULE_NAME , key ) ;
1506
- return newErrorDecision ( key , user , [ sprintf ( DECISION_MESSAGES . FLAG_KEY_INVALID , key ) ] ) ;
1507
- }
1508
-
1509
- const allDecideOptions = this . getAllDecideOptions ( options ) ;
1510
-
1511
- const forcedDecisionResponse = this . decisionService . findValidatedForcedDecision ( configObj , user , key ) ;
1512
- reasons . push ( ...forcedDecisionResponse . reasons ) ;
1513
- const variation = forcedDecisionResponse . result ;
1514
- if ( variation ) {
1515
- decisionObj = {
1516
- experiment : null ,
1517
- variation : variation ,
1518
- decisionSource : DECISION_SOURCES . FEATURE_TEST ,
1519
- } ;
1520
- } else {
1521
- const decisionVariation = this . decisionService . getVariationForFeature ( configObj , feature , user , allDecideOptions ) ;
1522
- reasons . push ( ...decisionVariation . reasons ) ;
1523
- decisionObj = decisionVariation . result ;
1524
- }
1525
- const decisionSource = decisionObj . decisionSource ;
1526
- const experimentKey = decisionObj . experiment ?. key ?? null ;
1527
- const variationKey = decisionObj . variation ?. key ?? null ;
1528
- const flagEnabled : boolean = decision . getFeatureEnabledFromVariation ( decisionObj ) ;
1529
- if ( flagEnabled === true ) {
1530
- this . logger . log ( LOG_LEVEL . INFO , LOG_MESSAGES . FEATURE_ENABLED_FOR_USER , MODULE_NAME , key , userId ) ;
1531
- } else {
1532
- this . logger . log ( LOG_LEVEL . INFO , LOG_MESSAGES . FEATURE_NOT_ENABLED_FOR_USER , MODULE_NAME , key , userId ) ;
1533
- }
1534
-
1535
- const variablesMap : { [ key : string ] : unknown } = { } ;
1536
- let decisionEventDispatched = false ;
1537
-
1538
- if ( ! allDecideOptions [ OptimizelyDecideOption . EXCLUDE_VARIABLES ] ) {
1539
- feature . variables . forEach ( variable => {
1540
- variablesMap [ variable . key ] = this . getFeatureVariableValueFromVariation (
1541
- key ,
1542
- flagEnabled ,
1543
- decisionObj . variation ,
1544
- variable ,
1545
- userId
1546
- ) ;
1547
- } ) ;
1548
- }
1500
+ options . filter ( option => option !== OptimizelyDecideOption . ENABLED_FLAGS_ONLY ) ;
1549
1501
1550
- if (
1551
- ! allDecideOptions [ OptimizelyDecideOption . DISABLE_DECISION_EVENT ] &&
1552
- ( decisionSource === DECISION_SOURCES . FEATURE_TEST ||
1553
- ( decisionSource === DECISION_SOURCES . ROLLOUT && projectConfig . getSendFlagDecisionsValue ( configObj ) ) )
1554
- ) {
1555
- this . sendImpressionEvent ( decisionObj , key , userId , flagEnabled , attributes ) ;
1556
- decisionEventDispatched = true ;
1557
- }
1558
-
1559
- const shouldIncludeReasons = allDecideOptions [ OptimizelyDecideOption . INCLUDE_REASONS ] ;
1560
-
1561
- let reportedReasons : string [ ] = [ ] ;
1562
- if ( shouldIncludeReasons ) {
1563
- reportedReasons = reasons . map ( reason => sprintf ( reason [ 0 ] as string , ...reason . slice ( 1 ) ) ) ;
1564
- }
1565
-
1566
- const featureInfo = {
1567
- flagKey : key ,
1568
- enabled : flagEnabled ,
1569
- variationKey : variationKey ,
1570
- ruleKey : experimentKey ,
1571
- variables : variablesMap ,
1572
- reasons : reportedReasons ,
1573
- decisionEventDispatched : decisionEventDispatched ,
1574
- } ;
1575
-
1576
- this . notificationCenter . sendNotifications ( NOTIFICATION_TYPES . DECISION , {
1577
- type : DECISION_NOTIFICATION_TYPES . FLAG ,
1578
- userId : userId ,
1579
- attributes : attributes ,
1580
- decisionInfo : featureInfo ,
1581
- } ) ;
1582
-
1583
- return {
1584
- variationKey : variationKey ,
1585
- enabled : flagEnabled ,
1586
- variables : variablesMap ,
1587
- ruleKey : experimentKey ,
1588
- flagKey : key ,
1589
- userContext : user ,
1590
- reasons : reportedReasons ,
1591
- } ;
1502
+ return this . decideForKeys ( user , [ key ] , options ) [ key ] ;
1592
1503
}
1593
1504
1594
1505
/**
@@ -1629,7 +1540,9 @@ export default class Optimizely implements Client {
1629
1540
options : OptimizelyDecideOption [ ] = [ ]
1630
1541
) : { [ key : string ] : OptimizelyDecision } {
1631
1542
const decisionMap : { [ key : string ] : OptimizelyDecision } = { } ;
1632
- if ( ! this . isValidInstance ( ) ) {
1543
+ const configObj = this . projectConfigManager . getConfig ( )
1544
+
1545
+ if ( ! this . isValidInstance ( ) || ! configObj ) {
1633
1546
this . logger . log ( LOG_LEVEL . ERROR , LOG_MESSAGES . INVALID_OBJECT , MODULE_NAME , 'decideForKeys' ) ;
1634
1547
return decisionMap ;
1635
1548
}
@@ -1638,12 +1551,111 @@ export default class Optimizely implements Client {
1638
1551
}
1639
1552
1640
1553
const allDecideOptions = this . getAllDecideOptions ( options ) ;
1641
- keys . forEach ( key => {
1642
- const optimizelyDecision : OptimizelyDecision = this . decide ( user , key , options ) ;
1643
- if ( ! allDecideOptions [ OptimizelyDecideOption . ENABLED_FLAGS_ONLY ] || optimizelyDecision . enabled ) {
1644
- decisionMap [ key ] = optimizelyDecision ;
1554
+
1555
+ for ( const key of keys ) {
1556
+ const feature = configObj . featureKeyMap [ key ] ;
1557
+ if ( ! feature ) {
1558
+ this . logger . log ( LOG_LEVEL . ERROR , ERROR_MESSAGES . FEATURE_NOT_IN_DATAFILE , MODULE_NAME , key ) ;
1559
+ decisionMap [ key ] = newErrorDecision ( key , user , [ sprintf ( DECISION_MESSAGES . FLAG_KEY_INVALID , key ) ] ) ;
1560
+ continue
1645
1561
}
1646
- } ) ;
1562
+
1563
+ const userId = user . getUserId ( ) ;
1564
+ const attributes = user . getAttributes ( ) ;
1565
+ const reasons : ( string | number ) [ ] [ ] = [ ] ;
1566
+ const forcedDecisionResponse = this . decisionService . findValidatedForcedDecision ( configObj , user , key ) ;
1567
+ reasons . push ( ...forcedDecisionResponse . reasons ) ;
1568
+ const variation = forcedDecisionResponse . result ;
1569
+ let decisionObj : DecisionObj ;
1570
+
1571
+ if ( variation ) {
1572
+ decisionObj = {
1573
+ experiment : null ,
1574
+ variation : variation ,
1575
+ decisionSource : DECISION_SOURCES . FEATURE_TEST ,
1576
+ } ;
1577
+ } else {
1578
+ const decisionVariation = this . decisionService . getVariationForFeature (
1579
+ configObj ,
1580
+ feature ,
1581
+ user ,
1582
+ allDecideOptions
1583
+ ) ;
1584
+ reasons . push ( ...decisionVariation . reasons ) ;
1585
+ decisionObj = decisionVariation . result ;
1586
+ }
1587
+
1588
+ const decisionSource = decisionObj . decisionSource ;
1589
+ const experimentKey = decisionObj . experiment ?. key ?? null ;
1590
+ const variationKey = decisionObj . variation ?. key ?? null ;
1591
+ const flagEnabled : boolean = decision . getFeatureEnabledFromVariation ( decisionObj ) ;
1592
+
1593
+ if ( flagEnabled ) {
1594
+ this . logger . log ( LOG_LEVEL . INFO , LOG_MESSAGES . FEATURE_ENABLED_FOR_USER , MODULE_NAME , key , userId ) ;
1595
+ } else {
1596
+ this . logger . log ( LOG_LEVEL . INFO , LOG_MESSAGES . FEATURE_NOT_ENABLED_FOR_USER , MODULE_NAME , key , userId ) ;
1597
+ }
1598
+
1599
+ const variablesMap : { [ key : string ] : unknown } = { } ;
1600
+ let decisionEventDispatched = false ;
1601
+
1602
+ if ( ! allDecideOptions [ OptimizelyDecideOption . EXCLUDE_VARIABLES ] ) {
1603
+ feature . variables . forEach ( variable => {
1604
+ variablesMap [ variable . key ] = this . getFeatureVariableValueFromVariation (
1605
+ key ,
1606
+ flagEnabled ,
1607
+ decisionObj . variation ,
1608
+ variable ,
1609
+ userId
1610
+ ) ;
1611
+ } ) ;
1612
+ }
1613
+
1614
+ if (
1615
+ ! allDecideOptions [ OptimizelyDecideOption . DISABLE_DECISION_EVENT ] &&
1616
+ ( decisionSource === DECISION_SOURCES . FEATURE_TEST ||
1617
+ ( decisionSource === DECISION_SOURCES . ROLLOUT && projectConfig . getSendFlagDecisionsValue ( configObj ) ) )
1618
+ ) {
1619
+ this . sendImpressionEvent ( decisionObj , key , userId , flagEnabled , attributes ) ;
1620
+ decisionEventDispatched = true ;
1621
+ }
1622
+
1623
+ const shouldIncludeReasons = allDecideOptions [ OptimizelyDecideOption . INCLUDE_REASONS ] ;
1624
+
1625
+ let reportedReasons : string [ ] = [ ] ;
1626
+ if ( shouldIncludeReasons ) {
1627
+ reportedReasons = reasons . map ( reason => sprintf ( reason [ 0 ] as string , ...reason . slice ( 1 ) ) ) ;
1628
+ }
1629
+
1630
+ const featureInfo = {
1631
+ flagKey : key ,
1632
+ enabled : flagEnabled ,
1633
+ variationKey : variationKey ,
1634
+ ruleKey : experimentKey ,
1635
+ variables : variablesMap ,
1636
+ reasons : reportedReasons ,
1637
+ decisionEventDispatched : decisionEventDispatched ,
1638
+ } ;
1639
+
1640
+ this . notificationCenter . sendNotifications ( NOTIFICATION_TYPES . DECISION , {
1641
+ type : DECISION_NOTIFICATION_TYPES . FLAG ,
1642
+ userId : userId ,
1643
+ attributes : attributes ,
1644
+ decisionInfo : featureInfo ,
1645
+ } ) ;
1646
+
1647
+ if ( ! allDecideOptions [ OptimizelyDecideOption . ENABLED_FLAGS_ONLY ] || flagEnabled ) {
1648
+ decisionMap [ key ] = {
1649
+ variationKey : variationKey ,
1650
+ enabled : flagEnabled ,
1651
+ variables : variablesMap ,
1652
+ ruleKey : experimentKey ,
1653
+ flagKey : key ,
1654
+ userContext : user ,
1655
+ reasons : reportedReasons ,
1656
+ } ;
1657
+ }
1658
+ }
1647
1659
1648
1660
return decisionMap ;
1649
1661
}
0 commit comments