@commercetools-frontend/application-components 22.3.4 → 22.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -40,6 +40,9 @@ var IconButton = require('@commercetools-uikit/icon-button');
40
40
  var Constraints = require('@commercetools-uikit/constraints');
41
41
  var PageNotFoundSVG = require('@commercetools-frontend/assets/images/page-not-found.svg');
42
42
  var FailedAuthorizationSVG = require('@commercetools-frontend/assets/images/doors-closed.svg');
43
+ var actionsGlobal = require('@commercetools-frontend/actions-global');
44
+ var applicationShellConnectors = require('@commercetools-frontend/application-shell-connectors');
45
+ var sentry = require('@commercetools-frontend/sentry');
43
46
  var _mapInstanceProperty = require('@babel/runtime-corejs3/core-js-stable/instance/map');
44
47
  var useResizeObserver = require('@react-hook/resize-observer');
45
48
  var hooks = require('@commercetools-uikit/hooks');
@@ -75,7 +78,7 @@ var _mapInstanceProperty__default = /*#__PURE__*/_interopDefault(_mapInstancePro
75
78
  var useResizeObserver__default = /*#__PURE__*/_interopDefault(useResizeObserver);
76
79
 
77
80
  // NOTE: This string will be replaced on build time with the package version.
78
- var version = "22.3.4";
81
+ var version = "22.5.0";
79
82
 
80
83
  var _context, _context2, _context3, _context4, _context5, _context6, _context7, _context8, _context9;
81
84
  const appKitSpacing55 = '40px';
@@ -550,7 +553,7 @@ const PageHeader = props => {
550
553
  PageHeader.propTypes = {};
551
554
  PageHeader.displayName = 'PageHeader';
552
555
 
553
- const ContentWrapper = /*#__PURE__*/_styled__default["default"]("div", {
556
+ const ContentWrapper$1 = /*#__PURE__*/_styled__default["default"]("div", {
554
557
  target: "e1b7jwn01"
555
558
  } )("flex:1;flex-basis:0;margin:", designTokens.marginForPageContent, ";overflow:auto;" + ("" ));
556
559
  const PageWrapper = /*#__PURE__*/_styled__default["default"]("div", {
@@ -560,7 +563,7 @@ const PageWrapper = /*#__PURE__*/_styled__default["default"]("div", {
560
563
  styles: "height:100%;display:flex;flex-direction:column"
561
564
  } );
562
565
 
563
- const messages$2 = reactIntl.defineMessages({
566
+ const messages$3 = reactIntl.defineMessages({
564
567
  back: {
565
568
  id: 'Components.ModalPage.TopBar.Back',
566
569
  defaultMessage: 'Go Back'
@@ -589,7 +592,8 @@ const LargeIconWrapper = props => jsxRuntime.jsx("span", {
589
592
  LargeIconWrapper.propTypes = {};
590
593
  const defaultProps$c = {
591
594
  color: 'surface',
592
- previousPathLabel: messages$2.back
595
+ previousPathLabel: messages$3.back,
596
+ hidePathLabel: false
593
597
  };
594
598
  var _ref$4 = {
595
599
  name: "uvw8rn",
@@ -601,7 +605,7 @@ const ModalPageTopBar = props => {
601
605
  css: /*#__PURE__*/react.css("position:relative;display:flex;align-items:center;justify-content:space-between;padding:", designTokens.paddingForModalTopBar, ";background-color:", props.color === 'neutral' ? designTokens.backgroundColorForPageHeader : designSystem.designTokens.colorSurface, ";border-bottom:1px solid ", props.color === 'neutral' ? designSystem.designTokens.colorSurface : designTokens.borderColorForModalTopBarWhenSurface, ";& *+*{margin-left:", designSystem.designTokens.spacingS, ";}p{font-size:12px!important;}" + ("" ), "" ),
602
606
  children: [jsxRuntime.jsxs("div", {
603
607
  css: _ref$4,
604
- children: [jsxRuntime.jsx(FlatButton__default["default"], {
608
+ children: [!props.hidePathLabel && jsxRuntime.jsx(FlatButton__default["default"], {
605
609
  tone: "primary",
606
610
  label: typeof props.previousPathLabel === 'string' ? props.previousPathLabel : intl.formatMessage(props.previousPathLabel),
607
611
  icon: jsxRuntime.jsx(icons.AngleLeftIcon, {
@@ -621,7 +625,7 @@ const ModalPageTopBar = props => {
621
625
  })]
622
626
  })]
623
627
  }), props.onClose && jsxRuntime.jsx(SecondaryIconButton__default["default"], {
624
- label: intl.formatMessage(messages$2.close),
628
+ label: intl.formatMessage(messages$3.close),
625
629
  onClick: props.onClose,
626
630
  icon: jsxRuntime.jsx(LargeIconWrapper, {
627
631
  children: jsxRuntime.jsx(icons.CloseIcon, {})
@@ -635,7 +639,7 @@ ModalPageTopBar.displayName = 'ModalPageTopBar';
635
639
  ModalPageTopBar.defaultProps = defaultProps$c;
636
640
 
637
641
  const TRANSITION_DURATION = 200;
638
- const getContainerStyles = _props => /*#__PURE__*/react.css("position:absolute;top:0;right:0;height:100%;width:100%;display:flex;flex-direction:column;background-color:", designSystem.customProperties.colorSurface, ";box-shadow:", designSystem.customProperties.shadow4, ",", designSystem.customProperties.shadow6, ";outline:0;transform:translate3d(30px, 0, 0);transition:transform ", TRANSITION_DURATION, "ms ease;" + ("" ), "" );
642
+ const getContainerStyles = _props => /*#__PURE__*/react.css("position:absolute;top:0;right:0;height:100%;width:", _props.size === 'small' ? '600px !important' : '100%', ";display:flex;flex-direction:column;background-color:", designSystem.customProperties.colorSurface, ";box-shadow:", designSystem.customProperties.shadow4, ",", designSystem.customProperties.shadow6, ";outline:0;transform:translate3d(30px, 0, 0);transition:transform ", TRANSITION_DURATION, "ms ease;" + ("" ), "" );
639
643
  const getOverlayStyles = props => /*#__PURE__*/react.css("position:absolute;z-index:", typeof props.zIndex === 'number' ? // Use `!important` to overwrite the default value assigned by the Stacking Layer System.
640
644
  "".concat(props.zIndex, " !important") : 'auto', ";top:0;left:0;width:100%;height:100%;background-color:rgba(32, 62, 72, 0.5);opacity:0;transition:opacity ", TRANSITION_DURATION, "ms ease;" + ("" ), "" );
641
645
  var _ref4 = {
@@ -675,7 +679,8 @@ jsxRuntime.jsx("div", _objectSpread$3(_objectSpread$3({}, props), {}, {
675
679
  // does not recognize the object shape.
676
680
  const defaultProps$b = {
677
681
  getParentSelector: getDefaultParentSelector,
678
- shouldDelayOnClose: true
682
+ shouldDelayOnClose: true,
683
+ size: 'large'
679
684
  };
680
685
  const ModalPage = props => {
681
686
  const _useState = react$1.useState(false),
@@ -721,7 +726,7 @@ const ModalPage = props => {
721
726
  beforeClose: makeClassName(getBeforeCloseOverlayAnimation())
722
727
  },
723
728
  className: {
724
- base: makeClassName(getContainerStyles()),
729
+ base: makeClassName(getContainerStyles(props)),
725
730
  afterOpen: typeof props.afterOpenStyles === 'string' ? props.afterOpenStyles : makeClassName((_props$afterOpenStyle = props.afterOpenStyles) !== null && _props$afterOpenStyle !== void 0 ? _props$afterOpenStyle : getAfterOpenContainerAnimation()),
726
731
  beforeClose: makeClassName(getBeforeCloseContainerAnimation())
727
732
  },
@@ -741,7 +746,8 @@ const ModalPage = props => {
741
746
  color: props.topBarColor,
742
747
  onClose: handleClose,
743
748
  currentPathLabel: props.currentPathLabel,
744
- previousPathLabel: props.previousPathLabel
749
+ previousPathLabel: props.previousPathLabel,
750
+ hidePathLabel: props.hidePathLabel
745
751
  }), props.children]
746
752
  });
747
753
  }
@@ -764,7 +770,7 @@ const InfoModalPage = props => jsxRuntime.jsxs(ModalPage, {
764
770
  children: [jsxRuntime.jsx(PageHeader, {
765
771
  title: props.title,
766
772
  subtitle: props.subtitle
767
- }), jsxRuntime.jsx(ContentWrapper, {
773
+ }), jsxRuntime.jsx(ContentWrapper$1, {
768
774
  children: props.children
769
775
  })]
770
776
  });
@@ -845,7 +851,7 @@ const CustomFormModalPage = props => jsxRuntime.jsxs(ModalPage, {
845
851
  alignItems: "flex-end",
846
852
  children: props.formControls
847
853
  })
848
- }), jsxRuntime.jsx(ContentWrapper, {
854
+ }), jsxRuntime.jsx(ContentWrapper$1, {
849
855
  children: props.children
850
856
  })]
851
857
  });
@@ -955,7 +961,7 @@ const TabularModalPage = props => {
955
961
  })
956
962
  })
957
963
  })]
958
- }), jsxRuntime.jsx(ContentWrapper, {
964
+ }), jsxRuntime.jsx(ContentWrapper$1, {
959
965
  children: props.children
960
966
  })]
961
967
  });
@@ -974,7 +980,7 @@ TabularModalPage.Intl = i18n.sharedMessages;
974
980
 
975
981
  const defaultProps$7 = {
976
982
  color: 'surface',
977
- previousPathLabel: messages$2.back
983
+ previousPathLabel: messages$3.back
978
984
  };
979
985
  const PageTopBar = props => {
980
986
  const intl = reactIntl.useIntl();
@@ -1026,7 +1032,7 @@ const CustomFormDetailPage = props => {
1026
1032
  children: props.formControls
1027
1033
  })
1028
1034
  })]
1029
- }), jsxRuntime.jsx(ContentWrapper, {
1035
+ }), jsxRuntime.jsx(ContentWrapper$1, {
1030
1036
  children: props.children
1031
1037
  })]
1032
1038
  });
@@ -1123,7 +1129,7 @@ const TabularDetailPage = props => {
1123
1129
  })
1124
1130
  })
1125
1131
  })]
1126
- }), jsxRuntime.jsx(ContentWrapper, {
1132
+ }), jsxRuntime.jsx(ContentWrapper$1, {
1127
1133
  children: props.children
1128
1134
  })]
1129
1135
  });
@@ -1142,7 +1148,7 @@ TabularDetailPage.PageHeaderTitle = PageHeaderTitle;
1142
1148
  // This is a convenience proxy export to expose pre-defined Intl messages defined in the `@commercetools-frontend/i18n` package.
1143
1149
  TabularDetailPage.Intl = i18n.sharedMessages;
1144
1150
 
1145
- const PublicPageLayout = /*#__PURE__*/react$1.lazy(() => Promise.resolve().then(function () { return require('./public-page-layout-992f709d.cjs.prod.js' /* webpackChunkName: "public-page-layout" */); }));
1151
+ const PublicPageLayout = /*#__PURE__*/react$1.lazy(() => Promise.resolve().then(function () { return require('./public-page-layout-b0cb3f87.cjs.prod.js' /* webpackChunkName: "public-page-layout" */); }));
1146
1152
 
1147
1153
  const MainPageContainer = /*#__PURE__*/_styled__default["default"]("div", {
1148
1154
  target: "ev8m2jf2"
@@ -1270,7 +1276,7 @@ const TabularMainPage = props => {
1270
1276
  })
1271
1277
  })
1272
1278
  })]
1273
- }), jsxRuntime.jsx(ContentWrapper, {
1279
+ }), jsxRuntime.jsx(ContentWrapper$1, {
1274
1280
  css: /*#__PURE__*/react.css("background-color:", designTokens.backgroundColorForTabularMainPageContent, ";" + ("" ), "" ),
1275
1281
  children: props.children
1276
1282
  })]
@@ -1329,7 +1335,7 @@ const MaintenancePageLayout = props => jsxRuntime.jsx("div", {
1329
1335
  MaintenancePageLayout.propTypes = {};
1330
1336
  MaintenancePageLayout.displayName = 'MaintenancePageLayout';
1331
1337
 
1332
- var messages$1 = reactIntl.defineMessages({
1338
+ var messages$2 = reactIntl.defineMessages({
1333
1339
  title: {
1334
1340
  id: 'PageNotFound.title',
1335
1341
  defaultMessage: 'We could not find what you are looking for'
@@ -1352,9 +1358,9 @@ const PageNotFound = () => {
1352
1358
  const intl = reactIntl.useIntl();
1353
1359
  return jsxRuntime.jsx(MaintenancePageLayout, {
1354
1360
  imageSrc: PageNotFoundSVG__default["default"],
1355
- title: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread$1({}, messages$1.title)),
1356
- label: intl.formatMessage(messages$1.title),
1357
- paragraph1: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread$1(_objectSpread$1({}, messages$1.paragraph1), {}, {
1361
+ title: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread$1({}, messages$2.title)),
1362
+ label: intl.formatMessage(messages$2.title),
1363
+ paragraph1: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread$1(_objectSpread$1({}, messages$2.paragraph1), {}, {
1358
1364
  values: {
1359
1365
  a: getLink
1360
1366
  }
@@ -1363,7 +1369,7 @@ const PageNotFound = () => {
1363
1369
  };
1364
1370
  PageNotFound.displayName = 'PageNotFound';
1365
1371
 
1366
- var messages = reactIntl.defineMessages({
1372
+ var messages$1 = reactIntl.defineMessages({
1367
1373
  title: {
1368
1374
  id: 'PageUnauthorized.title',
1369
1375
  defaultMessage: 'We could not find what you are looking for'
@@ -1390,10 +1396,10 @@ const PageUnauthorized = () => {
1390
1396
  const intl = reactIntl.useIntl();
1391
1397
  return jsxRuntime.jsx(MaintenancePageLayout, {
1392
1398
  imageSrc: FailedAuthorizationSVG__default["default"],
1393
- title: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread({}, messages.title)),
1394
- label: intl.formatMessage(messages.title),
1395
- paragraph1: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread({}, messages.paragraph1)),
1396
- paragraph2: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread(_objectSpread({}, messages.paragraph2), {}, {
1399
+ title: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread({}, messages$1.title)),
1400
+ label: intl.formatMessage(messages$1.title),
1401
+ paragraph1: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread({}, messages$1.paragraph1)),
1402
+ paragraph2: jsxRuntime.jsx(reactIntl.FormattedMessage, _objectSpread(_objectSpread({}, messages$1.paragraph2), {}, {
1397
1403
  values: {
1398
1404
  a: getSupportUrlLink
1399
1405
  }
@@ -1506,6 +1512,129 @@ function PageContentFull(props) {
1506
1512
  }
1507
1513
  PageContentFull.propTypes = {};
1508
1514
 
1515
+ const ContentWrapper = /*#__PURE__*/_styled__default["default"]("div", {
1516
+ target: "e1alzj9m0"
1517
+ } )("padding:", designSystem.designTokens.spacing40, " 40px;" + ("" ));
1518
+ function CustomPanel(props) {
1519
+ return jsxRuntime.jsx(ModalPage, {
1520
+ hidePathLabel: true,
1521
+ isOpen: true,
1522
+ onClose: props.onClose,
1523
+ size: props.size,
1524
+ title: props.title,
1525
+ children: jsxRuntime.jsx(ContentWrapper, {
1526
+ children: props.children
1527
+ })
1528
+ });
1529
+ }
1530
+ CustomPanel.propTypes = {};
1531
+
1532
+ const CUSTOM_VIEWS_EVENTS_NAMES = {
1533
+ CUSTOM_VIEW_BOOTSTRAP: 'custom-view-bootstrap',
1534
+ CUSTOM_VIEW_INITIALIZATION: 'custom-view-initialization'
1535
+ };
1536
+ const CUSTOM_VIEWS_EVENTS_META = {
1537
+ SOURCE: 'mc-host-application',
1538
+ DESTINATION_PREFIX: 'custom-view-'
1539
+ };
1540
+
1541
+ const messages = reactIntl.defineMessages({
1542
+ loadError: {
1543
+ id: 'Components.CustomViewLoader.error.load',
1544
+ defaultMessage: 'We could not load the Custom View. Please contact your administrator to check its configuration.'
1545
+ }
1546
+ });
1547
+
1548
+ const isIframeReady = iFrameElementRef => {
1549
+ try {
1550
+ var _iFrameElementRef$con;
1551
+ return (iFrameElementRef === null || iFrameElementRef === void 0 ? void 0 : (_iFrameElementRef$con = iFrameElementRef.contentWindow) === null || _iFrameElementRef$con === void 0 ? void 0 : _iFrameElementRef$con.document.readyState) === 'complete';
1552
+ } catch {
1553
+ // Trying to access the contentWindow of a cross-origin iFrame will throw an error.
1554
+ // We are not supposed to even get here because the iFrame must use
1555
+ // a URL from our very same domain (the custom view is proxied through our http-proxy service).
1556
+ return false;
1557
+ }
1558
+ };
1559
+ const CustomPanelIframe = /*#__PURE__*/_styled__default["default"]("iframe", {
1560
+ target: "ewwxuwo0"
1561
+ } )({
1562
+ name: "174lt7a",
1563
+ styles: "height:100%;width:100%;border:none"
1564
+ } );
1565
+ function CustomViewLoader(props) {
1566
+ var _props$customView$typ, _props$customView$typ2;
1567
+ const iFrameElementRef = react$1.useRef(null);
1568
+ const appContext = applicationShellConnectors.useApplicationContext();
1569
+ const iFrameCommunicationChannel = react$1.useRef(new MessageChannel());
1570
+ const showNotification = actionsGlobal.useShowNotification();
1571
+ const intl = reactIntl.useIntl();
1572
+ const panelSize = ((_props$customView$typ = props.customView.typeConfig) === null || _props$customView$typ === void 0 ? void 0 : (_props$customView$typ2 = _props$customView$typ.size) === null || _props$customView$typ2 === void 0 ? void 0 : _props$customView$typ2.toLocaleLowerCase()) || 'large';
1573
+ const messageFromIFrameHandler = react$1.useCallback(event => {
1574
+ if (event.data.origin === window.location.origin) {
1575
+ console.log('message received from iframe port: ', event);
1576
+ }
1577
+ }, []);
1578
+
1579
+ // onLoad handler is called from the iFrame even where the URL is not valid
1580
+ // (blocked by CORS, 404, etc.) so we need to make sure the iFrame is ready
1581
+ const onLoadSuccessHandler = react$1.useCallback(() => {
1582
+ var _iFrameElementRef$cur, _iFrameElementRef$cur2, _context, _appContext$user, _appContext$project;
1583
+ // Show error and block if the iFrame is not ready
1584
+ // (error loading it)
1585
+ if (!isIframeReady(iFrameElementRef.current)) {
1586
+ showNotification({
1587
+ domain: constants.DOMAINS.PAGE,
1588
+ kind: constants.NOTIFICATION_KINDS_PAGE.error,
1589
+ text: intl.formatMessage(messages.loadError)
1590
+ });
1591
+ return;
1592
+ }
1593
+
1594
+ // Listen for messages from the iFrame
1595
+ iFrameCommunicationChannel.current.port1.onmessage = messageFromIFrameHandler;
1596
+
1597
+ // Transfer port2 to the iFrame so it can send messages back privately
1598
+ (_iFrameElementRef$cur = iFrameElementRef.current) === null || _iFrameElementRef$cur === void 0 ? void 0 : (_iFrameElementRef$cur2 = _iFrameElementRef$cur.contentWindow) === null || _iFrameElementRef$cur2 === void 0 ? void 0 : _iFrameElementRef$cur2.postMessage(CUSTOM_VIEWS_EVENTS_NAMES.CUSTOM_VIEW_BOOTSTRAP, window.location.href, [iFrameCommunicationChannel.current.port2]);
1599
+
1600
+ // Send the initialization message to the iFrame
1601
+ iFrameCommunicationChannel.current.port1.postMessage({
1602
+ source: CUSTOM_VIEWS_EVENTS_META.SOURCE,
1603
+ destination: _concatInstanceProperty__default["default"](_context = "".concat(CUSTOM_VIEWS_EVENTS_META.DESTINATION_PREFIX)).call(_context, props.customView.id),
1604
+ eventName: CUSTOM_VIEWS_EVENTS_NAMES.CUSTOM_VIEW_INITIALIZATION,
1605
+ eventData: {
1606
+ context: {
1607
+ userLocale: (_appContext$user = appContext.user) === null || _appContext$user === void 0 ? void 0 : _appContext$user.locale,
1608
+ dataLocale: appContext.dataLocale,
1609
+ projectKey: (_appContext$project = appContext.project) === null || _appContext$project === void 0 ? void 0 : _appContext$project.key
1610
+ }
1611
+ }
1612
+ });
1613
+
1614
+ // We want the effect to run only once so we don't need the dependencies array.
1615
+ // eslint-disable-next-line react-hooks/exhaustive-deps
1616
+ }, []);
1617
+
1618
+ // Currently we only support custom panels
1619
+ if (props.customView.type !== 'CustomPanel') {
1620
+ sentry.reportErrorToSentry(new Error("CustomViewLoader: Provided Custom View has an unsupported type: ".concat(props.customView.type, ". Supported types: ['CustomPanel'].")));
1621
+ return null;
1622
+ }
1623
+ return jsxRuntime.jsx(CustomPanel, {
1624
+ title: "Custom View: ".concat(props.customView.defaultLabel),
1625
+ onClose: props.onClose,
1626
+ size: panelSize,
1627
+ children: jsxRuntime.jsx(CustomPanelIframe, {
1628
+ id: "custom-view-".concat(props.customView.id),
1629
+ ref: iFrameElementRef,
1630
+ title: "Custom View: ".concat(props.customView.defaultLabel),
1631
+ src: props.customView.url,
1632
+ onLoad: onLoadSuccessHandler
1633
+ }, "custom-view-".concat(props.customView.id))
1634
+ });
1635
+ }
1636
+ CustomViewLoader.propTypes = {};
1637
+
1509
1638
  // The width of each indentation level.
1510
1639
  const indentationSize = '48px';
1511
1640
  const useObserverElementDimensions = element => {
@@ -1624,6 +1753,8 @@ exports.ConfirmationDialog = ConfirmationDialog;
1624
1753
  exports.CustomFormDetailPage = CustomFormDetailPage;
1625
1754
  exports.CustomFormMainPage = CustomFormMainPage;
1626
1755
  exports.CustomFormModalPage = CustomFormModalPage;
1756
+ exports.CustomPanel = CustomPanel;
1757
+ exports.CustomViewLoader = CustomViewLoader;
1627
1758
  exports.FormDetailPage = FormDetailPage;
1628
1759
  exports.FormDialog = FormDialog;
1629
1760
  exports.FormMainPage = FormMainPage;