Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 4 additions & 7 deletions pages/api/payments/count/index.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,13 @@
import { CacheGet } from 'redis/index'
import { fetchUserProfileFromId } from 'services/userService'
import { fetchPaymentsCountByUserId } from 'services/transactionService'
import { setSession } from 'utils/setSession'

export default async (req: any, res: any): Promise<void> => {
if (req.method === 'GET') {
await setSession(req, res)
const userId = req.session.userId
const userReqTimezone = req.headers.timezone as string
const userProfile = await fetchUserProfileFromId(userId)
const userPreferredTimezone = userProfile?.preferredTimezone
const timezone = userPreferredTimezone !== '' ? userPreferredTimezone : userReqTimezone
const resJSON = await CacheGet.paymentsCount(userId, timezone)
const paybuttonId = (req.query.paybuttonId === '' || req.query.paybuttonId === undefined) ? undefined : req.query.paybuttonId as string
const paybuttonIds = paybuttonId !== undefined ? [paybuttonId] : undefined
const resJSON = await fetchPaymentsCountByUserId(userId, paybuttonIds)
res.status(200).json(resJSON)
}
}
4 changes: 2 additions & 2 deletions pages/api/payments/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ export default async (req: any, res: any): Promise<void> => {
const pageSize = req.query.pageSize as number
const orderDesc: boolean = !!(req.query.orderDesc === '' || req.query.orderDesc === undefined || req.query.orderDesc === 'true')
const orderBy = (req.query.orderBy === '' || req.query.orderBy === undefined) ? undefined : req.query.orderBy as string

const resJSON = await fetchAllPaymentsByUserIdWithPagination(userId, page, pageSize, orderBy, orderDesc)
const paybuttonId = (req.query.paybuttonId === '' || req.query.paybuttonId === undefined) ? undefined : req.query.paybuttonId as string
const resJSON = await fetchAllPaymentsByUserIdWithPagination(userId, page, pageSize, orderBy, orderDesc, paybuttonId)
res.status(200).json(resJSON)
}
}
55 changes: 39 additions & 16 deletions pages/payments/index.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { useEffect, useMemo, useState } from 'react'
import React, { useCallback, useEffect, useMemo, useState } from 'react'
import supertokensNode from 'supertokens-node'
import * as SuperTokensConfig from '../../config/backendConfig'
import Session from 'supertokens-node/recipe/session'
Expand All @@ -17,6 +17,7 @@ import TopBar from 'components/TopBar'
import { fetchUserWithSupertokens, UserWithSupertokens } from 'services/userService'
import { UserProfile } from '@prisma/client'
import Button from 'components/Button'
import { PaybuttonWithAddresses } from 'services/paybuttonService'

export const getServerSideProps: GetServerSideProps = async (context) => {
// this runs on the backend, so we must call init on supertokens-node SDK
Expand Down Expand Up @@ -57,6 +58,8 @@ export default function Payments ({ user, userId }: PaybuttonsProps): React.Reac
const [selectedCurrencyCSV, setSelectedCurrencyCSV] = useState<string>('')
const [paybuttonNetworks, setPaybuttonNetworks] = useState<Set<number>>(new Set())
const [loading, setLoading] = useState(false)
const [paybuttons, setPaybuttons] = useState<PaybuttonWithAddresses[]>()
const [selectedButton, setSelectedButton] = useState<string>('all')

const fetchPaybuttons = async (): Promise<any> => {
const res = await fetch(`/api/paybuttons?userId=${user?.userProfile.id}`, {
Expand All @@ -74,29 +77,36 @@ export default function Payments ({ user, userId }: PaybuttonsProps): React.Reac
return p.addresses.forEach((c: { address: { networkId: number } }) => networkIds.add(c.address.networkId))
})

setPaybuttons(paybuttons)
setPaybuttonNetworks(networkIds)
}

useEffect(() => {
void getDataAndSetUpCurrencyCSV()
}, [])

function fetchData (): Function {
return async (page: number, pageSize: number, orderBy: string, orderDesc: boolean) => {
const paymentsResponse = await fetch(`/api/payments?page=${page}&pageSize=${pageSize}&orderBy=${orderBy}&orderDesc=${String(orderDesc)}`)
const paymentsCountResponse = await fetch('/api/payments/count', {
headers: {
Timezone: timezone
const fetchData = useCallback(
(selectedButton: string): Function => {
return async (page: number, pageSize: number, orderBy: string, orderDesc: boolean) => {
const buttonFilter = selectedButton !== 'all' ? `&paybuttonId=${selectedButton}` : ''
const buttonFilterCount = selectedButton !== 'all' ? `?paybuttonId=${selectedButton}` : ''

const paymentsResponse = await fetch(`/api/payments?page=${page}&pageSize=${pageSize}&orderBy=${orderBy}&orderDesc=${String(orderDesc)}${buttonFilter}`)
const paymentsCountResponse = await fetch(`/api/payments/count${buttonFilterCount}`, {
headers: {
Timezone: timezone
}
})
const totalCount = await paymentsCountResponse.json()
const payments = await paymentsResponse.json()
return {
data: payments,
totalCount
}
})
const totalCount = await paymentsCountResponse.json()
const payments = await paymentsResponse.json()
return {
data: payments,
totalCount
}
}
}
},
[selectedButton, timezone]
)

const columns = useMemo(
() => [
Expand Down Expand Up @@ -215,6 +225,18 @@ export default function Payments ({ user, userId }: PaybuttonsProps): React.Reac
<>
<TopBar title="Payments" user={user?.stUser?.email} />
<div style={{ display: 'flex', alignItems: 'center', gap: '10px', justifyContent: 'right' }}>

<select
id="button-filter"
value={selectedButton}
onChange={(e) => setSelectedButton(e.target.value)}
className="select_button"
>
<option value="all">All Buttons</option>
{paybuttons?.map((button) => (
<option key={button.id} value={button.id}>{button.name}</option>
))}
</select>
{paybuttonNetworks.size > 1
? (
<select
Expand Down Expand Up @@ -247,8 +269,9 @@ export default function Payments ({ user, userId }: PaybuttonsProps): React.Reac
</Button>)}
</div>
<TableContainerGetter
key={selectedButton}
columns={columns}
dataGetter={fetchData()}
dataGetter={fetchData(selectedButton)}
tableRefreshCount={1}
emptyMessage='No Payments to show yet'
/>
Expand Down
17 changes: 17 additions & 0 deletions services/addressService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -339,3 +339,20 @@ export async function fetchAddressesByPaybuttonId (paybuttonId: string): Promise

return addressesIds
}

export async function fetchAddressesByPaybuttonIds (paybuttonIds: string[]): Promise<string[]> {
const addresses = await prisma.addressesOnButtons.findMany({
where: {
paybuttonId: {
in: paybuttonIds
}
}
})
const addressesIds = addresses.map(result => result.addressId)

if (addressesIds.length === 0) {
throw new Error(RESPONSE_MESSAGES.NO_ADDRESS_FOUND_404.message)
}

return addressesIds
}
74 changes: 66 additions & 8 deletions services/transactionService.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import prisma from 'prisma/clientInstance'
import { Prisma, Transaction } from '@prisma/client'
import { RESPONSE_MESSAGES, USD_QUOTE_ID, CAD_QUOTE_ID, N_OF_QUOTES, UPSERT_TRANSACTION_PRICES_ON_DB_TIMEOUT, SupportedQuotesType, NETWORK_IDS } from 'constants/index'
import { fetchAddressBySubstring, fetchAddressById, fetchAddressesByPaybuttonId, addressExists } from 'services/addressService'
import { fetchAddressBySubstring, fetchAddressById, fetchAddressesByPaybuttonId, addressExists, fetchAddressesByPaybuttonIds } from 'services/addressService'
import { AllPrices, QuoteValues, fetchPricesForNetworkAndTimestamp, flattenTimestamp } from 'services/priceService'
import _ from 'lodash'
import { CacheSet } from 'redis/index'
Expand Down Expand Up @@ -563,7 +563,8 @@ export async function getPaymentsByUserIdOrderedByButtonName (
userId: string,
page: number,
pageSize: number,
orderDesc = true
orderDesc = true,
paybuttonId?: string
): Promise<Payment[]> {
const offset = page * pageSize

Expand Down Expand Up @@ -596,7 +597,11 @@ export async function getPaymentsByUserIdOrderedByButtonName (
WHERE au.\`addressId\` = a.\`id\`
AND au.\`userId\` = ${userId}
)
AND t.\`amount\` > 0
AND p.\`providerUserId\` = ${userId}
AND (
${paybuttonId ?? null} IS NULL OR paybuttonId = ${paybuttonId}
)
GROUP BY t.id, p.id
ORDER BY p.\`name\` ASC
LIMIT ${pageSize}
Expand Down Expand Up @@ -631,6 +636,9 @@ export async function getPaymentsByUserIdOrderedByButtonName (
AND au.\`userId\` = ${userId}
)
AND p.\`providerUserId\` = ${userId}
AND (
${paybuttonId !== undefined ? paybuttonId : null} IS NULL OR paybuttonId = ${paybuttonId}
)
GROUP BY t.id, p.id
ORDER BY p.\`name\` DESC
LIMIT ${pageSize}
Expand Down Expand Up @@ -681,12 +689,13 @@ export async function fetchAllPaymentsByUserIdWithPagination (
page: number,
pageSize: number,
orderBy?: string,
orderDesc = true
orderDesc = true,
paybuttonId?: string
): Promise<Payment[]> {
const orderDescString: Prisma.SortOrder = orderDesc ? 'desc' : 'asc'
if (orderBy === 'buttonDisplayDataList') {
return await getPaymentsByUserIdOrderedByButtonName(
userId, page, pageSize, orderDesc
userId, page, pageSize, orderDesc, paybuttonId
)
}
let orderByQuery
Expand All @@ -712,8 +721,7 @@ export async function fetchAllPaymentsByUserIdWithPagination (
timestamp: orderDescString
}
}

const transactions = await prisma.transaction.findMany({
const query = {
where: {
address: {
userProfiles: {
Expand All @@ -724,13 +732,24 @@ export async function fetchAllPaymentsByUserIdWithPagination (
},
amount: {
gt: 0
}
},
addressId: {}
},
include: includePaybuttonsAndPrices,
orderBy: orderByQuery,
skip: page * Number(pageSize),
take: Number(pageSize)
})
}

let addressIdList = []
if (paybuttonId !== undefined) {
addressIdList = await fetchAddressesByPaybuttonId(paybuttonId)
query.where.addressId = {
in: addressIdList
}
}

const transactions = await prisma.transaction.findMany(query)

const transformedData: Payment[] = []
for (let index = 0; index < transactions.length; index++) {
Expand Down Expand Up @@ -783,3 +802,42 @@ export async function fetchTxCountByPaybuttonId (paybuttonId: string): Promise<n
}
})
}

export async function fetchPaymentsCountByUserId (userId: string, paybuttonIds?: string[]): Promise<number> {
if (paybuttonIds !== undefined) {
const addressIdList = await fetchAddressesByPaybuttonIds(paybuttonIds)

return await prisma.transaction.count({
where: {
address: {
userProfiles: {
some: {
userId
}
}
},
addressId: {
in: addressIdList
},
amount: {
gt: 0
}
}
})
} else {
return await prisma.transaction.count({
where: {
address: {
userProfiles: {
some: {
userId
}
}
},
amount: {
gt: 0
}
}
})
}
}