Skip to content

Commit

Permalink
Testing: Setup Playwright end-to-end testing and write first tests
Browse files Browse the repository at this point in the history
Fixes #432
  • Loading branch information
Innders committed May 20, 2024
2 parents 9cd0bc0 + c1d7797 commit f64f16e
Show file tree
Hide file tree
Showing 21 changed files with 262 additions and 76 deletions.
2 changes: 2 additions & 0 deletions src/app.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ import MarketPage from './pages/MarketPage'
import { RestartProvider } from './context/restartContext'
import { PasteProvider, PasteModal } from './context/pasteContext'
import FileUploadPreview from './containers/FileUploadPreview/FileUploadPreview'
import PreviewDialog from './containers/Preview/PreviewDialog'

const App = () => {
const user = useSelector((state) => state.user)
Expand Down Expand Up @@ -143,6 +144,7 @@ const App = () => {
>
<Header />
<ShareDialog />
<PreviewDialog />
<ConfirmDialog />
<FileUploadPreview />
<Routes>
Expand Down
8 changes: 4 additions & 4 deletions src/components/MarketAddonCard/MarketAddonCard.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,11 @@ const MarketAddonCard = ({
onInstall,
...props
}) => {
let state = 'install'
if (isInstalled && !isOutdated) state = 'installed'
let state = 'download'
if (isInstalled && !isOutdated) state = 'downloaded'
if (isInstalled && isOutdated) state = 'update'
if (isWaiting) state = 'pending'
if (isInstalling) state = isInstalled && isOutdated ? 'updating' : 'installing'
if (isInstalling) state = isInstalled && isOutdated ? 'updating' : 'downloading'
if (isFailed) state = 'failed'
if (isFinished) state = 'finished'

Expand All @@ -43,7 +43,7 @@ const MarketAddonCard = ({
if (state === 'update') stateVariant = 'filled'

const handleActionClick = () => {
if (['install', 'update'].includes(state)) {
if (['download', 'update'].includes(state)) {
onInstall(name, latestVersion)
}
}
Expand Down
8 changes: 4 additions & 4 deletions src/components/MarketAddonCard/MarketAddonCard.styled.js
Original file line number Diff line number Diff line change
Expand Up @@ -83,21 +83,21 @@ export const Tag = styled(Button)`
gap: var(--base-gap-small);
&.installed,
&.installing,
&.downloaded,
&.downloading,
&.pending,
&.updating,
&.finished {
background-color: unset;
user-select: none;
}
&.installed {
&.downloaded {
opacity: 0.5;
font-style: italic;
}
&.installing,
&.downloading,
&.updating {
.icon {
user-select: none;
Expand Down
7 changes: 7 additions & 0 deletions src/components/VersionSelectorTool/VersionSelectorTool.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
import * as Styled from './VersionSelectorTool.styled'

const VersionSelectorTool = ({ versions, selected, latest, approved, hero, onChange }) => {
return <Styled.Tools>VersionSelectorTool</Styled.Tools>
}

export default VersionSelectorTool
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import styled from 'styled-components'

export const Tools = styled.div`
display: flex;
align-items: center;
justify-content: flex-start;
flex: 1;
`
2 changes: 1 addition & 1 deletion src/containers/AddonSettings/AddonSettings.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -401,7 +401,7 @@ const AddonSettings = ({ projectName, showSites = false }) => {
}

if (!sameKeysStructure(oldValue, value)) {
toast.error('Icompatible data structure')
toast.error('Incompatible data structure')
console.log('Old value', oldValue)
console.log('New value', value)
return
Expand Down
13 changes: 9 additions & 4 deletions src/containers/AnatomyEditor.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -87,15 +87,20 @@ const AnatomyEditor = ({
toast.error('Invalid JSON')
return
}
const oldValue = getValueByPath(formData, path)
const oldValue = path.length === 0 ? formData : getValueByPath(formData, path)
if (oldValue === undefined) {
toast.error('No data to paste')
return
}
if (!sameKeysStructure(oldValue, value)) {
toast.error('Icompatible data structure')
toast.error('Incompatible data structure')
console.log('oldValue', oldValue)
console.log('value', value)
return
}

let newData = cloneDeep(formData)
newData = setValueByPath(formData, path, value)

newData = setValueByPath(newData, path, value)
setFormData(newData)
}

Expand Down
34 changes: 34 additions & 0 deletions src/containers/Preview/Preview.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { Button } from '@ynput/ayon-react-components'
import * as Styled from './Preview.styled'
import VersionSelectorTool from '/src/components/VersionSelectorTool/VersionSelectorTool'

const Preview = ({ selected = [], entityType, onClose }) => {
// TODO @LudoHolbik: a new services file src/services/preview/getPreview.js should be created for these queries below

// TODO @Innders: get selected entity data from selected and entityType

// TODO @LudoHolbik: get selected versions data from selected and entityType
// some entity types won't support this
// look at getActivities.js getEntityVersions [line 64] and getVersions [line 86] for reference
const allVersionsDummyData = [
{ id: 1, name: 'v001' },
{ id: 2, name: 'v002' },
{ id: 3, name: 'v003' },
{ id: 4, name: 'v004', hero: true },
{ id: 5, name: 'v005', status: 'approved' },
]

return (
<Styled.Container>
<Styled.Header>
<VersionSelectorTool versions={allVersionsDummyData} selected={selected} />
<Button onClick={onClose} icon={'close'} />
</Styled.Header>
<Styled.Content>
<h2>Selected Version: {selected.join(', ')}</h2>
</Styled.Content>
</Styled.Container>
)
}

export default Preview
22 changes: 22 additions & 0 deletions src/containers/Preview/Preview.styled.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { Toolbar } from '@ynput/ayon-react-components'
import styled from 'styled-components'

export const Container = styled.div`
display: flex;
flex-direction: column;
height: 100%;
overflow: hidden;
`

export const Header = styled(Toolbar)``
export const Content = styled.div`
flex: 1;
min-height: 80vh;
display: flex;
justify-content: center;
align-items: center;
h2 {
font-size: 2rem;
}
`
56 changes: 56 additions & 0 deletions src/containers/Preview/PreviewDialog.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import { Dialog } from '@ynput/ayon-react-components'
import { useDispatch, useSelector } from 'react-redux'
import { closePreview, openPreview } from '/src/features/preview'
import { useSearchParams } from 'react-router-dom'
import { useEffect } from 'react'
import Preview from './Preview'
import { isEqual } from 'lodash'
import styled from 'styled-components'

const StyledDialog = styled(Dialog)`
/* hide header and footer */
.header,
.footer {
display: none;
}
`

const PreviewDialog = () => {
const dispatch = useDispatch()
// check if dialog is open or not
const { selected, entityType } = useSelector((state) => state.preview)

const [searchParams, setUrlSearchParams] = useSearchParams()
// usually just one id is passed, but multiple ids can be passed
const selectedIds = searchParams.getAll('preview_id') || []
// passing undefined to openPreview will default to 'version'
const selectedType = searchParams.get('preview_type') || undefined
// when url has preview_id and preview_type, open the dialog if not already open

useEffect(() => {
if (!selectedIds.length) return
// check if dialog is already open with same ids
if (isEqual(selected, selectedIds)) return
// open the dialog
dispatch(openPreview({ selected: selectedIds, entityType: selectedType }))
}, [selectedIds, selectedType])

if (!selected.length) return null

const handleClose = () => {
// remove query params preview_id and preview_type from url
searchParams.delete('preview_id')
searchParams.delete('preview_type')
setUrlSearchParams(searchParams)
// close the dialog
dispatch(closePreview())
}

return (
<StyledDialog isOpen hideCancelButton size="full">
<Preview {...{ selected, entityType }} onClose={handleClose} />
</StyledDialog>
)
}

export default PreviewDialog
25 changes: 25 additions & 0 deletions src/features/preview.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import { createSlice } from '@reduxjs/toolkit'

const previewSlice = createSlice({
name: 'preview',
initialState: {
selected: [],
entityType: null,
},
reducers: {
openPreview: (state, { payload: { selected, entityType = 'version' } = {} } = {}) => {
state.selected = selected
state.entityType = entityType
},
updateSelection: (state, { payload: { selected } }) => {
state.selected = selected
},
closePreview: (state) => {
state.selected = []
state.entityType = null
},
},
})

export const { openPreview, updateSelection, closePreview } = previewSlice.actions
export default previewSlice.reducer
2 changes: 2 additions & 0 deletions src/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import editorReducer from './features/editor'
import dashboardReducer, { dashboardLocalItems } from './features/dashboard'
import detailsReducer, { detailsLocalItems } from './features/details'
import addonsManagerReducer from './features/addonsManager'
import previewReducer from './features/preview'

import App from './app'

Expand Down Expand Up @@ -40,6 +41,7 @@ const store = configureStore({
dashboard: dashboardReducer,
details: detailsReducer,
addonsManager: addonsManagerReducer,
preview: previewReducer,
[ayonApi.reducerPath]: ayonApi.reducer,
},
middleware: (getDefaultMiddleware) =>
Expand Down
16 changes: 8 additions & 8 deletions src/pages/MarketPage/AddonDetails/AddonDetails.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -85,13 +85,13 @@ const AddonDetails = ({ addon = {}, isLoading, onInstall, isUpdatingAll }) => {
if (isInstalling) {
actionButton = (
<SaveButton active saving disabled>
{isOutdated ? 'Updating' : 'Installing'}...
Downloading...
</SaveButton>
)
} else if (isFinished) {
actionButton = (
<Button disabled icon={'check_circle'}>
Installed!
Downloaded !
</Button>
)
} else if (isUpdatingAll) {
Expand All @@ -106,14 +106,14 @@ const AddonDetails = ({ addon = {}, isLoading, onInstall, isUpdatingAll }) => {
actionButton = (
<Button
variant="filled"
icon={'upgrade'}
icon={'download'}
onClick={handleInstall}
>{`Update to v${latestVersion}`}</Button>
>{`Download v${latestVersion}`}</Button>
)
} else if (latestVersion) {
actionButton = (
<Button variant="filled" icon={'download_for_offline'} onClick={handleInstall}>
{`Install v${latestVersion}`}
<Button variant="filled" icon={'download'} onClick={handleInstall}>
{`Download v${latestVersion}`}
</Button>
)
}
Expand Down Expand Up @@ -158,10 +158,10 @@ const AddonDetails = ({ addon = {}, isLoading, onInstall, isUpdatingAll }) => {
<Styled.Right className={classNames(Type.bodyMedium, { isLoading })}>
{actionButton}
<Styled.MetaPanel className={classNames({ isPlaceholder: isLoading })}>
<MetaPanelRow label="Installed Versions">
<MetaPanelRow label="Downloaded Versions">
{versionsToShow.length
? versionsToShow.map((version) => <span key={version}>{version}</span>)
: 'Not installed'}
: 'Not downloaded'}
{!!nOfMoreVersions && (
<span className="more" onClick={() => setShowAllVersions(true)}>
+{nOfMoreVersions} more
Expand Down
6 changes: 3 additions & 3 deletions src/pages/MarketPage/AddonFilters.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ const AddonFilters = ({ onSelect, onConnection }) => {
id: 'all',
name: 'All',
filter: [],
tooltip: 'All addons, installed or not',
tooltip: 'All addons, downloaded or not',
},
{
id: 'updates',
Expand All @@ -67,9 +67,9 @@ const AddonFilters = ({ onSelect, onConnection }) => {

{
id: 'uninstalled',
name: 'Not Installed',
name: 'Downloads Available',
filter: [{ isInstalled: false }],
tooltip: 'Addons available to install',
tooltip: 'Addons available to download',
},
]

Expand Down
3 changes: 1 addition & 2 deletions src/pages/MarketPage/MarketAddonsList.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,7 @@ const MarketAddonsList = ({
<Tag
icon={isUpdatingAll ? 'sync' : isUpdatingAllFinished ? 'check_circle' : 'upgrade'}
onClick={onUpdateAll}
className={isUpdatingAll ? 'installing' : ''}
className={isUpdatingAll ? 'downloading' : ''}
disabled={isUpdatingAll || isUpdatingAllFinished}
>
{isUpdatingAll ? 'Updating...' : isUpdatingAllFinished ? 'All Updated' : 'Update All'}
Expand All @@ -130,7 +130,6 @@ const MarketAddonsList = ({
onInstall={onInstall}
name={name}
{...props}
x
/>
)
})}
Expand Down
2 changes: 1 addition & 1 deletion src/pages/SettingsPage/AddonInstall/AddonUpload.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ const AddonUpload = ({ onClose, type = 'addon', onInstall, dropOnly, ...props })
console.log('finished: created ' + type)
return true
} catch (error) {
setErrorMessage(error?.response?.data?.detail)
setErrorMessage(error?.data?.detail)
console.error(error)
return false
}
Expand Down
4 changes: 2 additions & 2 deletions src/pages/SettingsPage/Bundles/BundleForm.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -86,8 +86,8 @@ const BundleForm = ({
<h2 style={{ margin: 0, marginRight: 32 }}>{formData?.installerVersion || 'NONE'}</h2>
<>
{!!installerPlatforms?.length &&
installerPlatforms.map((platform) => (
<Styled.PlatformTag key={platform} $platform={platform}>
installerPlatforms.map((platform, i) => (
<Styled.PlatformTag key={platform + '-' + i} $platform={platform}>
{upperFirst(platform === 'darwin' ? 'macOS' : platform)}
</Styled.PlatformTag>
))}
Expand Down
Loading

0 comments on commit f64f16e

Please sign in to comment.