"use strict";

exports.__esModule = true;
exports.default = UserNotification;

var _react = _interopRequireWildcard(require("react"));

var _styles = require("@mui/material/styles");

var _CardContent = _interopRequireDefault(require("@mui/material/CardContent"));

var _Comment = _interopRequireDefault(require("./Comment"));

var _UserFollow = _interopRequireDefault(require("./UserFollow"));

var _UndeletedFor = _interopRequireDefault(require("./UndeletedFor"));

var _DeletedFor = _interopRequireDefault(require("./DeletedFor"));

var _UserConnection = _interopRequireDefault(require("./UserConnection"));

var _PrivateMessage = _interopRequireDefault(require("./PrivateMessage"));

var _UserBlocked = _interopRequireDefault(require("./UserBlocked"));

var _Mention = _interopRequireDefault(require("./Mention"));

var _CollapsedFor = _interopRequireDefault(require("./CollapsedFor"));

var _KindlyNoticeFor = _interopRequireDefault(require("./KindlyNoticeFor"));

var _reactIntl = require("react-intl");

var _colors = require("@mui/material/colors");

var _KindlyNoticeFlag = _interopRequireDefault(require("./KindlyNoticeFlag"));

var _VoteUp = _interopRequireDefault(require("./VoteUp"));

var _Icon = _interopRequireDefault(require("@mui/material/Icon"));

var _Errors = require("../../constants/Errors");

var _contribution2 = require("../../utils/contribution");

var _ContributionFollow = _interopRequireDefault(require("./ContributionFollow"));

var _material = require("@mui/material");

var _IncubatorApproved = _interopRequireDefault(require("./IncubatorApproved"));

var _classnames = _interopRequireDefault(require("classnames"));

var _LoadingButton = _interopRequireDefault(require("@mui/lab/LoadingButton"));

var _Widget = _interopRequireDefault(require("../Widget"));

var _useThemeProps = _interopRequireDefault(require("@mui/material/styles/useThemeProps"));

var _BaseItem = _interopRequireDefault(require("../../shared/BaseItem"));

var _core = require("@selfcommunity/core");

const _excluded = ["id", "className", "notificationObject", "handleCustomNotification", "showMaxAggregated"];

function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }

function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }

function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }

function _extends() { _extends = Object.assign || function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); }

function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }

const messages = (0, _reactIntl.defineMessages)({
  receivePrivateMessage: {
    id: 'ui.notification.receivePrivateMessage',
    defaultMessage: 'ui.notification.receivePrivateMessage'
  }
});
const PREFIX = 'SCUserNotification';
const classes = {
  root: `${PREFIX}-root`,
  notificationWrap: `${PREFIX}-notification-wrap`,
  notificationHeader: `${PREFIX}-notification-header`,
  title: `${PREFIX}-title`,
  image: `${PREFIX}-image`,
  username: `${PREFIX}-username`,
  notificationContent: `${PREFIX}-notification-content`,
  notificationUnCollapsed: `${PREFIX}-notification-uncollapsed`,
  notificationCollapsed: `${PREFIX}-notification-collapsed`,
  stopNotificationButton: `${PREFIX}-stop-notification-button`,
  showOtherAggregated: `${PREFIX}-show-other-aggregated`
};
const Root = (0, _styles.styled)(_Widget.default, {
  name: PREFIX,
  slot: 'Root',
  overridesResolver: (props, styles) => styles.root
})(({
  theme
}) => ({
  width: '100%',
  marginBottom: theme.spacing(1),
  [`& .${classes.title}`]: {
    fontSize: 15,
    padding: `${theme.spacing()} ${theme.spacing(2)} 5px ${theme.spacing(2)}`,
    '&:hover': {
      textDecoration: 'underline'
    }
  },
  [`& .${classes.username}`]: {
    fontWeight: 700,
    '&:hover': {
      textDecoration: 'underline'
    }
  },
  [`& .${classes.notificationWrap}`]: {
    padding: `${theme.spacing()} 0px`
  },
  [`& .${classes.notificationContent}`]: {
    position: 'relative'
  },
  [`& .${classes.notificationHeader}`]: {
    boxSizing: 'border-box',
    boxShadow: 'none'
  },
  [`& .${classes.stopNotificationButton}`]: {
    margin: '5px 10px',
    padding: '2px 2px 2px 2px',
    minWidth: 'auto',
    '& span': {
      fontSize: 20
    }
  },
  [`& .${classes.showOtherAggregated}`]: {
    position: 'relative',
    top: theme.spacing(),
    backgroundColor: _colors.grey[100]
  },
  [`& .${classes.notificationCollapsed}`]: {
    paddingTop: theme.spacing()
  },
  '& a': {
    textDecoration: 'none',
    color: theme.palette.text.primary
  }
}));

/**
 *
 > API documentation for the Community-UI UserNotification component. Learn about the available props and the CSS API.

 #### Import

 ```jsx
 import {UserNotification} from '@selfcommunity/ui';
 ```

 #### Component Name

 The name `SCUserNotification` can be used when providing style overrides in the theme.


 #### CSS

 |Rule Name|Global class|Description|
 |---|---|---|
 |root|.SCUserNotification-root|Styles applied to the root element.|
 |notificationWrap|.SCUserNotification-notification-wrap|Styles applied to the element wrap.|
 |notificationHeader|.SCUserNotification-notification-wrap|Styles applied to the notification header.|
 |title|.SCUserNotification-title|Styles applied to the title element in the notification header.|
 |image|.SCUserNotification-image|Styles applied to the image element in the notification header.|
 |username|.SCUserNotification-username|Styles applied to the user element in the notification header.|
 |notificationContent|.SCUserNotification-notification-content|Styles applied to the notification content.|
 |notificationUnCollapsed|.SCUserNotification-notification-wrap|Styles applied to the uncollapsed elements.|
 |notificationCollapsed|.SCUserNotification-notification-wrap|Styles applied to the collapsed elements.|
 |stopNotificationButton|.SCUserNotification-stop-notification-button|Styles applied to the stop notification button.|
 |showOtherAggregated|.SCUserNotification-show-other-aggregated|Styles applied to the show other aggregated element.|

 * @param inProps
 */
function UserNotification(inProps) {
  // PROPS
  const props = (0, _useThemeProps.default)({
    props: inProps,
    name: PREFIX
  });

  const {
    id = `notification_${props.notificationObject.sid}`,
    className,
    notificationObject,
    handleCustomNotification,
    showMaxAggregated = 2
  } = props,
        rest = _objectWithoutPropertiesLoose(props, _excluded); // ROUTING


  const scRoutingContext = (0, _core.useSCRouting)(); // STATE

  const [obj, setObj] = (0, _react.useState)(notificationObject);
  const [loadingVote, setLoadingVote] = (0, _react.useState)(null);
  const [loadingSuspendNotification, setLoadingSuspendNotification] = (0, _react.useState)(false);
  const [openOtherAggregated, setOpenOtherAggregated] = (0, _react.useState)(false); //INTL

  const intl = (0, _reactIntl.useIntl)();
  /**
   * Performs  notification suspension
   */

  const performSuspendNotification = (0, _react.useMemo)(() => obj => {
    return _core.http.request({
      url: _core.Endpoints.UserSuspendContributionNotification.url({
        type: obj.type,
        id: obj.id
      }),
      method: _core.Endpoints.UserSuspendContributionNotification.method
    }).then(res => {
      if (res.status >= 300) {
        return Promise.reject(res);
      }

      return Promise.resolve(res.data);
    });
  }, [obj]);
  /**
   * Handles stop notification for contribution
   * @param contribution
   */

  function handleStopContentNotification(contribution) {
    setLoadingSuspendNotification(true);
    performSuspendNotification(contribution).then(data => {
      const newObj = obj;
      newObj[contribution.type].suspended = !newObj[contribution.type].suspended;
      setObj(newObj);
      setLoadingSuspendNotification(false);
    }).catch(error => {
      _core.Logger.error(_Errors.SCOPE_SC_UI, error);
    });
  }
  /**
   * Perform vote
   */


  const performVote = (0, _react.useMemo)(() => contribution => {
    return _core.http.request({
      url: _core.Endpoints.Vote.url({
        type: contribution.type,
        id: contribution.id
      }),
      method: _core.Endpoints.Vote.method
    }).then(res => {
      if (res.status >= 300) {
        return Promise.reject(res);
      }

      return Promise.resolve(res.data);
    });
  }, [obj]);
  /**
   * Handles vote
   * @param comment
   */

  function handleVote(index, contribution) {
    setLoadingVote(index);
    performVote(contribution).then(data => {
      const newObj = Object.assign({}, notificationObject);

      const _notification = Object.assign({}, newObj.aggregated[index]);

      const _contribution = _notification[contribution.type];
      _contribution.voted = !_contribution.voted;
      _contribution.vote_count = _contribution.vote_count - (_contribution.voted ? -1 : 1);
      _notification[contribution.type] = _contribution;
      newObj.aggregated[index] = _notification;
      setObj(newObj);
      setLoadingVote(null);
    }).catch(error => {
      _core.Logger.error(_Errors.SCOPE_SC_UI, error);
    });
  }
  /**
   * Render:
   * - discussion/post/status summary if notification include contribute
   * - user header for private message
   */


  function renderNotificationHeader() {
    /**
     * Private messages header
     */
    if (notificationObject.aggregated && notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.PRIVATE_MESSAGE) {
      let messageNotification = notificationObject.aggregated[0];
      return /*#__PURE__*/_react.default.createElement(_BaseItem.default, {
        className: classes.notificationHeader,
        image: /*#__PURE__*/_react.default.createElement(_core.Link, {
          to: scRoutingContext.url(_core.SCRoutes.USER_PROFILE_ROUTE_NAME, messageNotification.message.sender)
        }, /*#__PURE__*/_react.default.createElement(_material.Avatar, {
          alt: messageNotification.message.sender.username,
          variant: "circular",
          src: messageNotification.message.sender.avatar
        })),
        primary: /*#__PURE__*/_react.default.createElement(_material.Typography, {
          component: "span",
          color: "inherit"
        }, /*#__PURE__*/_react.default.createElement(_core.Link, {
          to: scRoutingContext.url(_core.SCRoutes.USER_PROFILE_ROUTE_NAME, messageNotification.message.sender),
          className: classes.username
        }, messageNotification.message.sender.username), ' ', intl.formatMessage(messages.receivePrivateMessage, {
          total: notificationObject.aggregated.length,
          b: (...chunks) => /*#__PURE__*/_react.default.createElement("strong", null, chunks)
        })),
        disableTypography: true
      });
    }
    /**
     * Comment, NestedComment, Follow Contribution header
     */


    if (notificationObject.aggregated && (notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.COMMENT || notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.NESTED_COMMENT || notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.FOLLOW || notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.MENTION || notificationObject.aggregated[0].type === _core.SCNotificationTypologyType.VOTE_UP)) {
      const contribution = (0, _contribution2.getContribution)(notificationObject);
      return /*#__PURE__*/_react.default.createElement("div", {
        className: classes.notificationHeader
      }, contribution && contribution.type !== _core.SCCommentTypologyType && /*#__PURE__*/_react.default.createElement(_material.Stack, {
        direction: "row",
        justifyContent: "space-between",
        alignItems: "center",
        spacing: 2
      }, /*#__PURE__*/_react.default.createElement(_core.Link, {
        to: scRoutingContext.url((0, _contribution2.getContributionRouteName)(contribution), notificationObject[contribution.type])
      }, /*#__PURE__*/_react.default.createElement(_material.Typography, {
        variant: "body2",
        gutterBottom: true,
        classes: {
          root: classes.title
        }
      }, (0, _contribution2.getContributionSnippet)(contribution))), contribution && /*#__PURE__*/_react.default.createElement(_material.Tooltip, {
        title: contribution.suspended ? /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, {
          id: 'ui.notification.notificationSuspended',
          defaultMessage: 'ui.notification.notificationSuspended'
        }) : /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, {
          id: 'ui.notification.notificationSuspend',
          defaultMessage: 'ui.notification.notificationSuspend'
        })
      }, /*#__PURE__*/_react.default.createElement(_LoadingButton.default, {
        variant: "text",
        size: "small",
        loading: loadingSuspendNotification,
        color: 'inherit',
        classes: {
          root: classes.stopNotificationButton
        },
        onClick: () => handleStopContentNotification(contribution)
      }, contribution.suspended ? /*#__PURE__*/_react.default.createElement(_Icon.default, {
        fontSize: "small",
        color: 'primary'
      }, "notifications_off") : /*#__PURE__*/_react.default.createElement(_Icon.default, {
        fontSize: "small",
        color: 'inherit'
      }, "notifications")))));
    }

    return null;
  }
  /**
   * Render every single notification in aggregated group
   * @param n
   * @param i
   */


  function renderAggregatedItem(n, i) {
    if (n.type === _core.SCNotificationTypologyType.COMMENT || n.type === _core.SCNotificationTypologyType.NESTED_COMMENT) {
      return /*#__PURE__*/_react.default.createElement(_Comment.default, {
        notificationObject: n,
        key: i,
        index: i,
        onVote: handleVote,
        loadingVote: loadingVote
      });
    } else if (n.type === _core.SCNotificationTypologyType.FOLLOW) {
      return /*#__PURE__*/_react.default.createElement(_ContributionFollow.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.USER_FOLLOW) {
      return /*#__PURE__*/_react.default.createElement(_UserFollow.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.CONNECTION_REQUEST || n.type === _core.SCNotificationTypologyType.CONNECTION_ACCEPT) {
      return /*#__PURE__*/_react.default.createElement(_UserConnection.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.VOTE_UP) {
      return /*#__PURE__*/_react.default.createElement(_VoteUp.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_ADVERTISING || n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_AGGRESSIVE || n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_POOR || n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_VULGAR || n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_OFFTOPIC) {
      return /*#__PURE__*/_react.default.createElement(_KindlyNoticeFor.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.KINDLY_NOTICE_FLAG) {
      return /*#__PURE__*/_react.default.createElement(_KindlyNoticeFlag.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.DELETED_FOR_ADVERTISING || n.type === _core.SCNotificationTypologyType.DELETED_FOR_AGGRESSIVE || n.type === _core.SCNotificationTypologyType.DELETED_FOR_POOR || n.type === _core.SCNotificationTypologyType.DELETED_FOR_VULGAR || n.type === _core.SCNotificationTypologyType.DELETED_FOR_OFFTOPIC) {
      return /*#__PURE__*/_react.default.createElement(_DeletedFor.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.UNDELETED_FOR) {
      return /*#__PURE__*/_react.default.createElement(_UndeletedFor.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.COLLAPSED_FOR_ADVERTISING || n.type === _core.SCNotificationTypologyType.COLLAPSED_FOR_AGGRESSIVE || n.type === _core.SCNotificationTypologyType.COLLAPSED_FOR_POOR || n.type === _core.SCNotificationTypologyType.COLLAPSED_FOR_VULGAR || n.type === _core.SCNotificationTypologyType.COLLAPSED_FOR_OFFTOPIC) {
      return /*#__PURE__*/_react.default.createElement(_CollapsedFor.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.PRIVATE_MESSAGE) {
      return /*#__PURE__*/_react.default.createElement(_PrivateMessage.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.BLOCKED_USER || n.type === _core.SCNotificationTypologyType.UNBLOCKED_USER) {
      return /*#__PURE__*/_react.default.createElement(_UserBlocked.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.MENTION) {
      return /*#__PURE__*/_react.default.createElement(_Mention.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.INCUBATOR_APPROVED) {
      return /*#__PURE__*/_react.default.createElement(_IncubatorApproved.default, {
        notificationObject: n,
        key: i
      });
    } else if (n.type === _core.SCNotificationTypologyType.CUSTOM_NOTIFICATION) {
      handleCustomNotification && handleCustomNotification(n);
    }

    return null;
  }
  /**
   * Renders root object
   */


  return /*#__PURE__*/_react.default.createElement(Root, _extends({
    id: id,
    className: (0, _classnames.default)(classes.root, className)
  }, rest), /*#__PURE__*/_react.default.createElement(_CardContent.default, {
    classes: {
      root: classes.notificationWrap
    }
  }, renderNotificationHeader(), /*#__PURE__*/_react.default.createElement("div", {
    className: classes.notificationContent
  }, /*#__PURE__*/_react.default.createElement("div", {
    className: classes.notificationUnCollapsed
  }, notificationObject.aggregated.slice(0, showMaxAggregated).map((n, i) => renderAggregatedItem(n, i))), notificationObject.aggregated.length > showMaxAggregated && /*#__PURE__*/_react.default.createElement(_react.default.Fragment, null, /*#__PURE__*/_react.default.createElement(_material.ListItemButton, {
    onClick: () => setOpenOtherAggregated(prev => !prev),
    classes: {
      root: classes.showOtherAggregated
    }
  }, /*#__PURE__*/_react.default.createElement(_material.ListItemText, {
    primary: /*#__PURE__*/_react.default.createElement(_reactIntl.FormattedMessage, {
      id: 'ui.notification.showOthers',
      defaultMessage: 'ui.notification.showOthers'
    })
  }), openOtherAggregated ? /*#__PURE__*/_react.default.createElement(_Icon.default, null, "expand_less") : /*#__PURE__*/_react.default.createElement(_Icon.default, null, "expand_more")), /*#__PURE__*/_react.default.createElement(_material.Collapse, {
    in: openOtherAggregated,
    timeout: "auto",
    unmountOnExit: true,
    classes: {
      root: classes.notificationCollapsed
    }
  }, notificationObject.aggregated.slice(showMaxAggregated).map((n, i) => renderAggregatedItem(n, i)))))));
}