Skip to content
This repository has been archived by the owner on Oct 4, 2023. It is now read-only.

[C-850, C-950] Add AudioTransactionsPage and display test data in AudioTransactionsTable #2033

Merged
merged 1 commit into from
Oct 3, 2022
Merged
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
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
.textContainer {
position: relative;
display: inline-flex;
gap: 4px;
max-width: 100%;
}

.textCell {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
line-height: 1.2;
}

.changeCell.increase {
color: var(--accent-green);
}
.changeCell.decrease {
color: var(--accent-orange);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,213 @@
import { useCallback, useMemo } from 'react'

import {
formatNumberCommas,
TransactionMethod,
TransactionType
} from '@audius/common'
import cn from 'classnames'
import moment from 'moment'
import { ColumnInstance } from 'react-table'

import { AudioTransactionIcon } from 'components/audio-transaction-icon'
import { TestTable } from 'components/test-table'

import styles from './AudioTransactionsTable.module.css'

const transactionTypeLabelMap: Record<TransactionType, string> = {
[TransactionType.TRANSFER]: '$AUDIO',
[TransactionType.CHALLENGE_REWARD]: '$AUDIO Reward Earned',
[TransactionType.TRENDING_REWARD]: 'Trending Competition Award',
[TransactionType.TIP]: 'Tip',
[TransactionType.PURCHASE]: 'Purchased $AUDIO'
}

const transactionMethodLabelMap: Record<TransactionMethod, string | null> = {
[TransactionMethod.COINBASE]: null,
[TransactionMethod.STRIPE]: null,
[TransactionMethod.RECEIVE]: 'Received',
[TransactionMethod.SEND]: 'Sent'
}

export type AudioTransactionsTableColumn =
| 'balance'
| 'change'
| 'date'
| 'transactionIcon'
| 'transactionType'
| 'spacer'
| 'spacer2'

type AudioTransactionsTableProps = {
columns?: AudioTransactionsTableColumn[]
data: any[]
isVirtualized?: boolean
loading?: boolean
onClickRow?: (collectible: any, index: number) => void
tableClassName?: string
wrapperClassName?: string
}

const defaultColumns: AudioTransactionsTableColumn[] = [
'spacer',
'transactionIcon',
'transactionType',
'date',
'change',
'balance',
'spacer2'
]

export const AudioTransactionsTable = ({
columns = defaultColumns,
data,
isVirtualized = false,
loading = false,
onClickRow,
tableClassName,
wrapperClassName
}: AudioTransactionsTableProps) => {
// Cell Render Functions
const renderTransactionIconCell = useCallback((cellInfo) => {
const { transactionType, method } = cellInfo.row.original
return <AudioTransactionIcon type={transactionType} method={method} />
}, [])

const renderTransactionTypeCell = useCallback((cellInfo) => {
const { transactionType, method } = cellInfo.row.original
const typeText = transactionTypeLabelMap[transactionType as TransactionType]
const methodText =
transactionMethodLabelMap[method as TransactionMethod] ?? ''

const isTransferType =
transactionType === TransactionType.TIP ||
transactionType === TransactionType.TRANSFER

return `${typeText} ${isTransferType ? methodText : ''}`.trim()
}, [])

const renderBalanceCell = useCallback((cellInfo) => {
const transaction = cellInfo.row.original
return formatNumberCommas(transaction.balance)
}, [])

const renderDateCell = useCallback((cellInfo) => {
const transaction = cellInfo.row.original
return moment(transaction.date).format('M/D/YY')
}, [])

const renderChangeCell = useCallback((cellInfo) => {
const { change } = cellInfo.row.original
return (
<div
className={cn(styles.changeCell, {
[styles.increase]: Number(change) > 0,
[styles.decrease]: Number(change) < 0
})}
>
{Number(change) > 0 ? '+' : ''}
{change}
</div>
)
}, [])

// Columns
const tableColumnMap: Record<
AudioTransactionsTableColumn,
Partial<ColumnInstance>
> = useMemo(
() => ({
transactionIcon: {
id: 'transactionIcon',
accessor: '',
Cell: renderTransactionIconCell,
minWidth: 64,
maxWidth: 64,
disableResizing: true,
disableSortBy: true
},
transactionType: {
id: 'transactionType',
Header: 'Transaction Type',
accessor: 'type',
Cell: renderTransactionTypeCell,
width: 150,
disableSortBy: true,
align: 'left'
},
date: {
id: 'date',
Header: 'Date',
accessor: 'date',
Cell: renderDateCell,
disableSortBy: true,
align: 'right'
},
change: {
id: 'change',
Header: 'Change',
accessor: 'change',
Cell: renderChangeCell,
disableSortBy: true,
align: 'right'
},
balance: {
id: 'balance',
Header: 'Balance',
accessor: 'balance',
Cell: renderBalanceCell,
disableSortBy: true,
align: 'right'
},
spacer: {
id: 'spacer',
maxWidth: 24,
minWidth: 24,
disableSortBy: true,
disableResizing: true
},
spacer2: {
id: 'spacer2',
maxWidth: 24,
minWidth: 24,
disableSortBy: true,
disableResizing: true
}
}),
[
renderTransactionIconCell,
renderTransactionTypeCell,
renderDateCell,
renderChangeCell,
renderBalanceCell
]
)

const tableColumns = useMemo(
() => columns.map((id) => tableColumnMap[id]),
[columns, tableColumnMap]
)

const handleClickRow = useCallback(
(rowInfo, index: number) => {
const transaction = rowInfo.original
onClickRow?.(transaction, index)
},
[onClickRow]
)

const getRowClassName = useCallback(() => '', [])

return (
<TestTable
wrapperClassName={wrapperClassName}
tableClassName={tableClassName}
getRowClassName={getRowClassName}
columns={tableColumns}
data={data}
loading={loading}
onClickRow={handleClickRow}
isVirtualized={isVirtualized}
/>
)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { AudioTransactionsTable } from './AudioTransactionsTable'
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,7 @@
align-items: center;
vertical-align: middle;
justify-content: center;
height: 64px;
padding: 20px 12px;
background: transparent;
user-select: none;
Expand Down
8 changes: 4 additions & 4 deletions packages/web/src/components/tracks-table/TracksTable.js
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ const artistNameCell = (val, record, props) => {
return `${record.user?.name} [Deactivated]`
}
return (
<ArtistPopover handle={record.handle}>
<ArtistPopover handle={record.handle ?? ''}>
<div
className={styles.textContainer}
onClick={(e) => {
Expand Down Expand Up @@ -133,7 +133,7 @@ const optionsButtonCell = (
props,
storeActionButtonRefs
) => {
const deleted = record.is_delete || !!record.user.is_deactivated
const deleted = record.is_delete || !!record.user?.is_deactivated
const optionsButtonRef = createRef()
storeActionButtonRefs(record.key, optionsButtonRef)

Expand All @@ -150,8 +150,8 @@ const optionsButtonCell = (
date={val.date}
isFavorited={val.has_current_user_saved}
isOwner={record.owner_id === props.userId}
isOwnerDeactivated={!!record.user.is_deactivated}
isArtistPick={val.user._artist_pick === val.track_id}
isOwnerDeactivated={!!record.user?.is_deactivated}
isArtistPick={val.user?._artist_pick === val.track_id}
index={index}
trackTitle={val.name}
albumId={null}
Expand Down
8 changes: 8 additions & 0 deletions packages/web/src/pages/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ import TrendingGenreSelectionPage from 'components/trending-genre-selection/Tren
import AnnouncementPage from 'pages/announcement-page/AnnoucementPage'
import ArtistDashboardPage from 'pages/artist-dashboard-page/ArtistDashboardPage'
import { AudioRewardsPage } from 'pages/audio-rewards-page/AudioRewardsPage'
import { AudioTransactionsPage } from 'pages/audio-transactions-page'
import CheckPage from 'pages/check-page/CheckPage'
import CollectionPage from 'pages/collection-page/CollectionPage'
import EmptyPage from 'pages/empty-page/EmptyPage'
Expand Down Expand Up @@ -100,6 +101,7 @@ import {
HISTORY_PAGE,
DASHBOARD_PAGE,
AUDIO_PAGE,
AUDIO_TRANSACTIONS_PAGE,
UPLOAD_PAGE,
UPLOAD_ALBUM_PAGE,
UPLOAD_PLAYLIST_PAGE,
Expand Down Expand Up @@ -783,6 +785,12 @@ class App extends Component {
isMobile={isMobileClient}
component={AudioRewardsPage}
/>
<Route
exact
path={AUDIO_TRANSACTIONS_PAGE}
isMobile={isMobileClient}
component={AudioTransactionsPage}
/>
<Route
exact
path={DEACTIVATE_PAGE}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/* Body Content Wrapper */
.bodyWrapper {
display: flex;
flex-direction: column;
position: relative;
}

/* Track Table */
.bodyWrapper .tableWrapper {
width: 100%;
border-radius: 8px;
box-shadow: 0 2px 5px -2px var(--tile-shadow-3);
background-color: var(--white);
margin-bottom: 35px;
padding-bottom: 5px;
overflow: hidden;
}

.spinner {
width: 40px;
height: 40px;
margin: 0 auto;
}

.spinner g path {
stroke: var(--secondary) !important;
}
Loading