stacker.news/components/subscribeUser.js
SatsAllDay 992fc54160
Subscription management page (#1000)
* first pass of a subscription management page under settings

* add tabs to settings ui

* NymActionDropdown

* update Apollo InMemoryCache to merge paginated list of my subscribed users

* various updates

* switch from UsersNullable to Users

* bake the nym action dropdwon into the user component

* add back fields to the user query

* `meSubscriptionPosts`, `meSubscriptionComments`, `meMute`

* Refetch my subscribed users when a user subscription is changed

* update user list to hide stats in the subscribed list users

* update my sub'd users fragment to remove unnecessary user fields

* memoize subscribe user context provider value to avoid re-renders

* use inner join instead of left join

Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>

* throw error when unauthenticated

Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>

---------

Co-authored-by: Keyan <34140557+huumn@users.noreply.github.com>
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
2024-04-03 19:38:47 -05:00

64 lines
1.9 KiB
JavaScript

import { createContext, useContext } from 'react'
import { useMutation } from '@apollo/client'
import { gql } from 'graphql-tag'
import Dropdown from 'react-bootstrap/Dropdown'
import { useToast } from './toast'
const SubscribeUserContext = createContext(() => ({
refetchQueries: []
}))
export const SubscribeUserContextProvider = ({ children, value }) => {
return (
<SubscribeUserContext.Provider value={value}>
{children}
</SubscribeUserContext.Provider>
)
}
export const useSubscribeUserContext = () => useContext(SubscribeUserContext)
export default function SubscribeUserDropdownItem ({ user, target = 'posts' }) {
const isPosts = target === 'posts'
const mutation = isPosts ? 'subscribeUserPosts' : 'subscribeUserComments'
const userField = isPosts ? 'meSubscriptionPosts' : 'meSubscriptionComments'
const toaster = useToast()
const { id, [userField]: meSubscription } = user
const { refetchQueries } = useSubscribeUserContext()
const [subscribeUser] = useMutation(
gql`
mutation ${mutation}($id: ID!) {
${mutation}(id: $id) {
${userField}
}
}`, {
refetchQueries,
update (cache, { data: { [mutation]: subscribeUser } }) {
cache.modify({
id: `User:${id}`,
fields: {
[userField]: () => subscribeUser[userField]
}
})
}
}
)
return (
<Dropdown.Item
onClick={async () => {
try {
await subscribeUser({ variables: { id } })
toaster.success(meSubscription ? 'unsubscribed' : 'subscribed')
} catch (err) {
console.error(err)
toaster.danger(meSubscription ? 'failed to unsubscribe' : 'failed to subscribe')
}
}}
>
{meSubscription
? `unsubscribe from ${isPosts ? 'posts' : 'comments'}`
: `subscribe to ${isPosts ? 'posts' : 'comments'}`}
</Dropdown.Item>
)
}