@apollo/react-hooks#useSubscription JavaScript Examples

The following examples show how to use @apollo/react-hooks#useSubscription. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: DonationsDashboard.js    From lifebank with MIT License 4 votes vote down vote up
DonationsDashboard = ({ isDesktop, currentUser, isOffer, selectOffer }) => {
  const { t } = useTranslation('translations')
  const [maxWidth] = useState('md')
  const [maxWidthQr] = useState('xs')
  const [open, setOpen] = useState(false)
  const [accountTo, setAccountTo] = useState()
  const [openModalQR, setOpenModalQR] = useState(false)
  const [scanValue, setScanValue] = useState()
  const [tokens, setTokens] = useState(0)
  const [role] = useState(currentUser.role)
  const [account] = useState(currentUser.account)
  const classes = useStyles()
  const [openSnackbar, setOpenSnackbar] = useState(false)
  const [state, setState] = useState({
    bottom: false
  })
  const theme = useTheme()
  const isSmallScreen = useMediaQuery(theme.breakpoints.down(370))
  const history = useHistory()
  const [
    loadProfile,
    { error: errroLoadProfile, data: { profile: { profile } = {} } = {}, client }
  ] = useLazyQuery(PROFILE_QUERY, { fetchPolicy: 'network-only' })

  const { data: tokenUser = {} } = useSubscription(
    TOKEN_SUBSCRIPTION, { variables: { account } }
  )
  const [
    donate,
    { loading, error, data: { donate: donateResult } = {} }
  ] = useMutation(DONATE_MUTATION)

  const handleSnackbarClose = () => {
    setOpenSnackbar({ ...openSnackbar, show: false })
    setAccountTo()
  }

  useEffect(() => {
    if (!error)
      return

    setOpenSnackbar({
      show: true,
      message: t('donations.donationsError'),
      severity: 'error'
    })
  }, [t, error])

  useEffect(() => {
    if (errroLoadProfile) {
      handleOpen()
      setOpenSnackbar({
        show: true,
        message: t('donations.donationsProfileError'),
        severity: 'error'
      })
    }

  }, [t, errroLoadProfile])

  useEffect(() => {
    if (!donateResult)
      return

    setOpenSnackbar({
      show: true,
      message: t('donations.succesful'),
      severity: 'success'
    })
  }, [t, donateResult])

  useEffect(() => {
    if (!currentUser) {
      client && client.resetStore()
      history.replace('/')

      return
    }

    if (state.bottom === true || open === true)
      loadProfile()

  }, [currentUser, history, client, loadProfile, state, open, donateResult])

  useEffect(() => {
    if (tokenUser.user) {
      setTokens(parseInt(tokenUser.user[0].token))
    } else {
      setTokens(role === "donor" && profile?.balance.length ? profile.balance.join(',').split(' ')[0] : 0)
    }
  }, [role, profile, tokenUser])

  const anchor = 'bottom'

  const toggleDrawer = (anchor, open) => (event) => {
    if (event) {
      if (
        event.type === 'keydown' &&
        (event.key === 'Tab' || event.key === 'Shift')
      )
        return

      setState({ ...state, [anchor]: open })
    }
  }

  const handleOpen = () => setOpen(!open)

  const handleOpenModalQr = () => setOpenModalQR(!openModalQR)

  const handlerTransferTokens = (account) => {
    setAccountTo(account)
  }

  useEffect(() => {
    if (profile && accountTo) {
      let tempMemo
      if (role === "donor") tempMemo = t("donations.memoDonor")
      else tempMemo = t("donations.memoLifebank")

      const tokensQuantity = 1

      const payload = {
        to: accountTo.toLowerCase().replace(/\s/g, ''),
        memo: tempMemo,
        quantity: tokensQuantity,
        emailContent: {
          'subject': t('emailDonorCongratulation.subject'),
          'content': t('emailDonorCongratulation.hi').concat(
            ' ',
            accountTo,
            ', ',
            '<br><br>',
            t('emailDonorCongratulation.youComplete'),
            ' ',
            profile.name,
            ' ',
            t('emailDonorCongratulation.receivedTokens'),
            ' ',
            tokensQuantity,
            ' ',
            tokensQuantity > 1? t('emailDonorCongratulation.lifeTokensMany'): t('emailDonorCongratulation.lifeTokens'),
            ' ',
            t('emailDonorCongratulation.thanksYou'),
            '<br><br>',
            t('emailDonorCongratulation.growingCommunity'),
          ),
          "badge": t('emailDonorCongratulation.badgeUrl'),
          "content2": t('emailDonorCongratulation.downloadBadge').concat(
            '<br><br>',
            t('emailDonorCongratulation.thanksAgain')
          )
        }
      }
      donate({
        variables: {
          ...payload
        }
      })
    }
  }, [t, donate, role, accountTo])


  const DashboardContent = () => {
    const [accountInput, setAccountInput] = useState("")

    const handleChangeAccountInput = (event) => {
      setAccountInput(event.target.value)
    }
    
    useEffect(() => {
      if (scanValue) setAccountInput(scanValue)
    }, [scanValue])

    return (
      <Box className={classes.dashboardContent}>
        {isDesktop && (
          <>
            <Box className={classes.closeIcon}>
              <IconButton
                aria-label="close"
                color="inherit"
                size="small"
                onClick={handleOpen}
              >
                <CloseIcon fontSize="inherit" />
              </IconButton>
            </Box>
            {role === "donor" &&
              <Typography className={classes.draweTitleDesktop}>
                {t('donations.donate')}
              </Typography>
            }
            {role === "lifebank" &&
              <Typography className={classes.draweTitleDesktop}>
                {t('donations.transferTokens')}
              </Typography>
            }
            {role === "sponsor" &&
              <Typography className={classes.draweTitleDesktop}>
                {t('donations.claimReward')}
              </Typography>
            }
          </>
        )}
        {!isDesktop && (
          <>
            <Box className={classes.closeIcon}>
              <IconButton
                aria-label="close"
                color="inherit"
                size="small"
                onClick={toggleDrawer(anchor, false)}
              >
                <CloseIcon fontSize="inherit" />
              </IconButton>
            </Box>
            {role === "donor" &&
              <Typography className={classes.draweTitle}>
                {t('donations.yourDonationsAndRewards')}
              </Typography>
            }
            {role === "lifebank" &&
              <Typography className={classes.draweTitle}>
                {t('donations.transferTokens')}
              </Typography>
            }
            {role === "sponsor" &&
              <Typography className={classes.draweTitle}>
                {t('donations.claimReward')}
              </Typography>
            }
            <Divider className={classes.dividerTitle} />
          </>
        )}
        {role === "donor" &&
          <Box className={classes.boxBalance}>
            <Typography className={classes.balanceText}>
              {t('donations.youOwn')}
            </Typography>
            <EmptyHeartSVG balance={parseInt(tokens)} isDesktop={isDesktop} />
            <Typography className={classes.balanceText}>
              {t('miscellaneous.tokens')}
            </Typography>
          </Box>
        }
        { (role === "donor" || role === "sponsor") &&
          <Box>
            {role === "donor" &&
              <Box>
                <Typography className={classes.sectionTitle}>
                  {t('donations.receiveTokens')}
                </Typography>
                <Divider className={classes.dividerSection} />
                <Typography className={classes.sectionText}>
                  {t('donations.toReceiveTokens')}
                </Typography>
              </Box>
            }
            {role === "sponsor" &&
              <Typography className={classes.sectionText}>
                {t('donations.toReceiveTokensDonor')}
              </Typography>
            }
            <Box className={classes.boxQR}>
              <QRCode value={account} size={100} />
              <Typography className={classes.accountText}>
                {account}
              </Typography>
            </Box>
          </Box>
        }
        { (role === "donor" || role === "lifebank") &&
          <Box>
            {role === "donor" &&
              <Box>
                <Typography className={classes.sectionTitle}>
                  {t('donations.sendTokens')}
                </Typography>
                <Divider className={classes.dividerSection} />
                <Typography className={classes.sectionText}>
                  {t('donations.toSendTo')}
                </Typography>
              </Box>
            }
            {role === "lifebank" &&
              <Typography className={classes.sectionText}>
                {t('donations.toSendToDonor')}
              </Typography>
            }
            <Box className={classes.boxTexfield}>
              <form autoComplete="off">
                <TextField
                  className={classes.inputText}
                  id="paylod-account"
                  label={role === "lifebank" ? t('donations.enterDonorUsername') : t('donations.enterSponsorUsername')}
                  variant="filled"
                  value={accountInput}
                  onChange={handleChangeAccountInput}
                />
                <QrReaderModal setAccountInput={setAccountInput} />
              </form>
            </Box>
            <Box className={classes.boxButtonSendToken}>
              {loading &&
                <>
                  <CircularProgress />
                  <br />
                  <br />
                </>
              }
              <Button className={classes.sendTokenButton} variant="contained" color="secondary"
                onClick={() => {
                  handlerTransferTokens(accountInput)
                }}
                disabled={
                  !accountInput ||
                  loading
                }
              >
                {t('donations.sendToken')}
              </Button>
            </Box>
          </Box>
        }
      </Box>
    )
  }

  const Transition = forwardRef(function Transition(props, ref) {
    return <Slide direction="up" ref={ref} {...props} />
  })

  const QrReaderModal = () => {
    const theme = useTheme()
    const fullScreen = useMediaQuery(theme.breakpoints.down('sm'))
    const [cameraSelection, setCameraSelction] = useState("rear")
    const succesefulScan = (value) => {
      if (value) {
        setOpenModalQR(false)
        setScanValue(value)
      }
    }

    useEffect(() => {
      if (openModalQR) {
        setScanValue("")
      }
    }, [openModalQR])

    const handleChangeCamera = () => {
      if (cameraSelection === "rear") setCameraSelction("front")
      else setCameraSelction("rear")
    }

    return (
      <>
        <IconButton aria-label="delete" className={classes.camaraButtonIcon} onClick={handleOpenModalQr}>
          <CameraAltIcon className={classes.camaraIcon} />
        </IconButton>
        <Dialog
          fullScreen={fullScreen}
          maxWidth={maxWidthQr}
          open={openModalQR}
          onClose={handleOpenModalQr}
          aria-labelledby="transition-modal-title"
          aria-describedby="transition-modal-description"
          closeAfterTransition
          BackdropComponent={Backdrop}
          BackdropProps={{
            timeout: 500
          }}
          TransitionComponent={Transition}
        >
          {fullScreen &&
            <AppBar className={classes.appBar}>
              <Toolbar>
                <IconButton
                  className={classes.backIcon}
                  onClick={handleOpenModalQr}
                  aria-label="close"
                >
                  <KeyboardBackspaceIcon />
                </IconButton>
                <Typography variant="h6" className={classes.titleScanQR}>
                  {t('donations.scanQR')}
                </Typography>
                <IconButton
                  className={classes.switchCamaraIcon}
                  onClick={handleChangeCamera}
                  aria-label="close"
                >
                  <FlipCameraIosIcon />
                </IconButton>
              </Toolbar>
            </AppBar>
          }
          {!fullScreen &&
            <Box className={classes.dialog}>
              <Box className={classes.closeIcon}>
                <IconButton
                  aria-label="close"
                  color="inherit"
                  size="small"
                  onClick={handleOpenModalQr}
                >
                  <CloseIcon fontSize="inherit" />
                </IconButton>
              </Box>
              <Typography className={classes.titleScanQR}>
                {t('donations.scanQR')}
              </Typography>
            </Box>
          }
          {cameraSelection &&
            <QrReader
              delay={100}
              onError={() => { }}
              onScan={(value) => { succesefulScan(value) }}
              facingMode={cameraSelection}
              style={{
                height: "auto",
                width: "100%",
                backgroundColor: '#ffffff',
              }}
            />
          }
        </Dialog>
      </>
    )
  }

  return (
    <>
      {!isDesktop && (
        <>
          { role === "donor" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButton}
              onClick={toggleDrawer(anchor, true)}
            >
              <FavoriteIcon className={classes.iconFab} />
              {!isSmallScreen &&
                t('donations.donate')
              }
            </Fab>
          }
          { role === "lifebank" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButton}
              onClick={toggleDrawer(anchor, true)}
            >
              <FavoriteIcon className={classes.iconFab} />
              {!isSmallScreen &&
                t('donations.transferTokens')
              }
            </Fab>
          }
          { role === "sponsor" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButton}
              onClick={toggleDrawer(anchor, true)}
            >
              <ShoppingCartIcon className={classes.iconFab} />
              {!isSmallScreen &&
                t('donations.claimReward')
              }
            </Fab>
          }
          <Drawer
            anchor={anchor}
            open={state[anchor]}
            onClose={toggleDrawer(anchor, false)}
            PaperProps={{
              elevation: 0,
              style: {
                borderTopLeftRadius: '20px',
                borderTopRightRadius: '20px',
                padding: '16px',
              }
            }}
          >
            <DashboardContent />
          </Drawer >
        </>
      )}
      {isDesktop &&
        <>
          {
            role === "donor" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButtonDesktop}
              onClick={handleOpen}
            >
              <FavoriteIcon className={classes.iconFab} />
              {t('donations.donate')}
            </Fab>
          }
          {
            role === "lifebank" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButtonDesktop}
              onClick={handleOpen}
            >
              <FavoriteIcon className={classes.iconFab} />
              {t('donations.transferTokens')}
            </Fab>
          }
          {
            role === "sponsor" && !isOffer &&
            <Fab
              color="secondary"
              variant="extended"
              className={classes.fabButtonDesktop}
              onClick={handleOpen}
            >
              <ShoppingCartIcon className={classes.iconFab} />
              {t('donations.claimReward')}
            </Fab>
          }
          <Dialog
            maxWidth={maxWidth}
            open={open}
            onClose={handleOpen}
            aria-labelledby="transition-modal-title"
            aria-describedby="transition-modal-description"
            closeAfterTransition
            BackdropComponent={Backdrop}
            BackdropProps={{
              timeout: 500
            }}
          >
            <Box className={classes.dialog}>
              <DashboardContent />
            </Box>
          </Dialog>
        </>
      }
      <Snackbar open={openSnackbar.show} autoHideDuration={2000} onClose={handleSnackbarClose}>
        <Alert severity={openSnackbar.severity}>
          {openSnackbar.message}
        </Alert>
      </Snackbar>
    </>
  )
}
Example #2
Source File: Notification.js    From lifebank with MIT License 4 votes vote down vote up
Notification = () => {
  const { t } = useTranslation('translations')
  const classes = useStyles()
  const [open, setOpen] = useState(false)
  const location = useLocation()
  const [limit, setLimit] = useState(10)
  const isHome = location.pathname === '/'
  const theme = useTheme()
  const [currentUser] = useUser()
  const [account] = useState(currentUser.account)
  const [notifications, setNotifications] = useState([])
  const [notificationStatus, setNotificationStatus] = useState(true)
  const trigger = useScrollTrigger({
    target: window || undefined,
    disableHysteresis: true
  })
  const isDesktop = useMediaQuery(theme.breakpoints.up('md'), {
    defaultMatches: true
  })
  const useTransparentBG = isDesktop && !trigger && isHome

  const handleClickOpen = () => {
    setOpen(true)
  }

  const handleClose = () => {
    setLimit(10)
    setOpen(false)
  }

  const handleMoreNotifications = () => {
    setLimit(limit + 10)
    setNotificationStatus(true)
  }

  const { loading: loadingNotifications, data: notification = {} }
    = useSubscription(NOTIFICATION_SUBSCRIPTION, { variables: { account_to: account, limit: limit } })

  useEffect(() => {
    if (Object.keys(notification).length) {
      const notificationList = notification.notification
      setNotifications(notificationList)
    }
  }, [notification])

  useEffect(() => {

    if (notification.notification) {
      var i
      for (i = 0; i < notification.notification.length; i++) {
        if (notification.notification[i].state) {
          setNotificationStatus(false)
          break
        } else {
          setNotificationStatus(true)
        }
      }
    }

  }, [notification])

  return (
    <>
      <IconButton className={classes.wrapper} onClick={handleClickOpen}>
        {notificationStatus &&
          <NotificationsIcon
            alt="Notification icon"
            className={clsx(classes.notificationIcon, {
              [classes.notificationIconTransparent]: useTransparentBG
            })}
          />}
        {!notificationStatus &&
          <NotificationsActiveIcon
            alt="Notification icon"
            className={clsx(classes.notificationIcon, {
              [classes.notificationIconTransparent]: useTransparentBG
            })}
          />}
      </IconButton>
      <Dialog className={classes.box}
        fullScreen
        open={open}
        onClose={handleClose}
        TransitionComponent={Transition}
      >
        <AppBar className={classes.appBar}>
          <Toolbar >
            <Typography variant="h6" className={classes.title}>
              {t('miscellaneous.recentActivity')}
            </Typography>
          </Toolbar>
        </AppBar>
        <List>
          {notifications.length > 0 && (
            <>
              {notifications.map((element, key) => (
                <NotificationStructure
                  key={key}
                  id={element.id}
                  title={element.title}
                  description={element.description}
                  state={element.state}
                  dateAndTime={element.created_at}
                />
              ))}
            </>
          )}
        </List>
        <Box className={classes.showMoreBox}>
          {!loadingNotifications &&
            <Button variant="contained" className={classes.showMore} color="primary" onClick={handleMoreNotifications}>
              {t('common.loadMore')}
            </Button>
          }
          {loadingNotifications && <CircularProgress />}
        </Box>
      </Dialog>
    </>
  )
}