Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
D
dify
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
ai-tech
dify
Commits
1ee00cba
Commit
1ee00cba
authored
Jun 09, 2023
by
StyleZhang
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
fix: notion-page-selector
parent
6b884ab2
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
82 additions
and
20 deletions
+82
-20
index.tsx
web/app/components/base/notion-icon/index.tsx
+2
-2
base.tsx
web/app/components/base/notion-page-selector/base.tsx
+5
-0
index.tsx
...ponents/base/notion-page-selector/page-selector/index.tsx
+72
-17
index.module.css
...s/base/notion-page-selector/search-input/index.module.css
+2
-0
index.tsx
...mponents/base/notion-page-selector/search-input/index.tsx
+1
-1
No files found.
web/app/components/base/notion-icon/index.tsx
View file @
1ee00cba
...
...
@@ -16,7 +16,7 @@ const NotionIcon = ({
}:
NotionIconProps
)
=>
{
if
(
type
===
'workspace'
)
{
if
(
src
)
{
if
(
src
.
includes
(
'https
://'
))
{
if
(
src
.
startsWith
(
'https://'
)
||
src
.
startsWith
(
'http
://'
))
{
return
(
<
img
alt=
'workspace icon'
...
...
@@ -35,7 +35,7 @@ const NotionIcon = ({
}
if
(
src
)
{
if
(
src
.
includes
(
'https
://'
))
{
if
(
src
.
startsWith
(
'https://'
)
||
src
.
startsWith
(
'http
://'
))
{
return
(
<
img
alt=
'page icon'
...
...
web/app/components/base/notion-page-selector/base.tsx
View file @
1ee00cba
...
...
@@ -10,12 +10,14 @@ import AccountSetting from '@/app/components/header/account-setting'
import
type
{
DataSourceNotionPage
}
from
'@/models/common'
type
NotionPageSelectorProps
=
{
value
?:
string
[]
onSelect
:
(
selectedPages
:
(
DataSourceNotionPage
&
{
workspace_id
:
string
})[])
=>
void
canPreview
?:
boolean
onPreview
?:
(
selectedPage
:
DataSourceNotionPage
&
{
workspace_id
:
string
})
=>
void
}
const
NotionPageSelector
=
({
value
,
onSelect
,
canPreview
,
onPreview
,
...
...
@@ -77,6 +79,9 @@ const NotionPageSelector = ({
{
currentWorkspace
?.
source_info
.
pages
.
length
&&
(
<
PageSelector
key=
{
currentWorkspaceId
}
value=
{
value
}
searchValue=
{
searchValue
}
list=
{
currentWorkspace
?.
source_info
.
pages
}
onSelect=
{
handleSelecPages
}
canPreview=
{
canPreview
}
...
...
web/app/components/base/notion-page-selector/page-selector/index.tsx
View file @
1ee00cba
import
{
memo
,
useState
}
from
'react'
import
{
memo
,
use
Effect
,
use
State
}
from
'react'
import
{
useTranslation
}
from
'react-i18next'
import
{
FixedSizeList
as
List
,
areEqual
}
from
'react-window'
import
type
{
ListChildComponentProps
}
from
'react-window'
...
...
@@ -9,6 +9,8 @@ import s from './index.module.css'
import
type
{
DataSourceNotionPage
}
from
'@/models/common'
type
PageSelectorProps
=
{
value
?:
string
[]
searchValue
:
string
list
:
DataSourceNotionPage
[]
onSelect
:
(
selectedPages
:
DataSourceNotionPage
[])
=>
void
canPreview
?:
boolean
...
...
@@ -19,6 +21,7 @@ type NotionPageTreeItem = {
children
:
Set
<
string
>
descendants
:
Set
<
string
>
deepth
:
number
ancestors
:
string
[]
}
&
DataSourceNotionPage
type
NotionPageTreeMap
=
Record
<
string
,
NotionPageTreeItem
>
type
NotionPageItem
=
{
...
...
@@ -45,6 +48,7 @@ const recursivePushInParentDescendants = (
children
,
descendants
,
deepth
:
0
,
ancestors
:
[],
}
}
else
{
...
...
@@ -53,6 +57,7 @@ const recursivePushInParentDescendants = (
listTreeMap
[
parentId
].
descendants
.
add
(
leafItem
.
page_id
)
}
leafItem
.
deepth
++
leafItem
.
ancestors
.
unshift
(
listTreeMap
[
parentId
].
page_name
)
if
(
listTreeMap
[
parentId
].
parent_id
!==
'root'
)
recursivePushInParentDescendants
(
listMap
,
listTreeMap
,
listTreeMap
[
parentId
],
leafItem
)
...
...
@@ -66,10 +71,16 @@ const Item = memo(({ index, style, data }: ListChildComponentProps<{
handleCheck
:
(
index
:
number
)
=>
void
canPreview
?:
boolean
handlePreview
:
(
index
:
number
)
=>
void
listMapWithChildrenAndDescendants
:
NotionPageTreeMap
searchValue
:
string
}
>
)
=>
{
const
{
t
}
=
useTranslation
()
const
{
dataList
,
handleToggle
,
checkedIds
,
handleCheck
,
canPreview
,
handlePreview
}
=
data
const
{
dataList
,
handleToggle
,
checkedIds
,
handleCheck
,
canPreview
,
handlePreview
,
listMapWithChildrenAndDescendants
,
searchValue
}
=
data
const
current
=
dataList
[
index
]
const
currentWithChildrenAndDescendants
=
listMapWithChildrenAndDescendants
[
current
.
page_id
]
const
hasChild
=
currentWithChildrenAndDescendants
.
descendants
.
size
>
0
const
ancestors
=
currentWithChildrenAndDescendants
.
ancestors
const
breadCrumbs
=
ancestors
.
length
?
[...
ancestors
,
current
.
page_name
]
:
[
current
.
page_name
]
let
iconSrc
if
(
current
.
page_icon
&&
current
.
page_icon
.
type
===
'url'
)
...
...
@@ -78,6 +89,20 @@ const Item = memo(({ index, style, data }: ListChildComponentProps<{
if
(
current
.
page_icon
&&
current
.
page_icon
.
type
===
'emoji'
)
iconSrc
=
current
.
page_icon
.
emoji
const
renderArrow
=
()
=>
{
return
hasChild
?
(
<
div
className=
{
cn
(
s
.
arrow
,
current
.
expand
&&
s
[
'arrow-expand'
],
'shrink-0 mr-1 w-5 h-5 hover:bg-gray-200 rounded-md'
)
}
style=
{
{
marginLeft
:
current
.
deepth
*
8
}
}
onClick=
{
()
=>
handleToggle
(
index
)
}
/>
)
:
(
<
div
className=
'shrink-0 mr-1 w-5 h-5'
style=
{
{
marginLeft
:
current
.
deepth
*
8
}
}
/>
)
}
return
(
<
div
className=
'group flex items-center pl-2 pr-[2px] rounded-md hover:bg-gray-100 cursor-pointer'
...
...
@@ -88,11 +113,7 @@ const Item = memo(({ index, style, data }: ListChildComponentProps<{
checked=
{
checkedIds
.
has
(
current
.
page_id
)
}
onCheck=
{
()
=>
handleCheck
(
index
)
}
/>
<
div
className=
{
cn
(
s
.
arrow
,
current
.
expand
&&
s
[
'arrow-expand'
],
'shrink-0 mr-1 w-5 h-5 hover:bg-gray-200 rounded-md'
)
}
style=
{
{
marginLeft
:
current
.
deepth
*
8
}
}
onClick=
{
()
=>
handleToggle
(
index
)
}
/>
{
!
searchValue
&&
renderArrow
()
}
<
NotionIcon
className=
'shrink-0 mr-1'
type=
'page'
...
...
@@ -107,17 +128,29 @@ const Item = memo(({ index, style, data }: ListChildComponentProps<{
{
canPreview
&&
(
<
div
className=
'shrink-0 hidden group-hover:flex items-center ml-
4
px-2 h-6 rounded-md text-xs font-medium text-gray-700 cursor-pointer hover:bg-gray-50'
className=
'shrink-0 hidden group-hover:flex items-center ml-
1
px-2 h-6 rounded-md text-xs font-medium text-gray-700 cursor-pointer hover:bg-gray-50'
onClick=
{
()
=>
handlePreview
(
index
)
}
>
{
t
(
'common.dataSource.notion.selector.preview'
)
}
</
div
>
)
}
{
searchValue
&&
(
<
div
className=
'shrink-0 ml-1 max-w-[120px] text-xs text-gray-400 truncate'
title=
{
breadCrumbs
.
join
(
' / '
)
}
>
{
breadCrumbs
.
join
(
' / '
)
}
</
div
>
)
}
</
div
>
)
},
areEqual
)
const
PageSelector
=
({
value
,
searchValue
,
list
,
onSelect
,
canPreview
=
true
,
...
...
@@ -132,7 +165,8 @@ const PageSelector = ({
}
}),
)
const
[
checkedIds
,
setCheckedIds
]
=
useState
<
Set
<
string
>>
(
new
Set
())
const
[
searchDataList
,
setSearchDataList
]
=
useState
<
NotionPageItem
[]
>
([])
const
[
checkedIds
,
setCheckedIds
]
=
useState
<
Set
<
string
>>
(
new
Set
(
value
||
[]))
const
listMap
=
list
.
reduce
((
prev
:
NotionPageMap
,
next
:
DataSourceNotionPage
)
=>
{
prev
[
next
.
page_id
]
=
next
...
...
@@ -141,7 +175,7 @@ const PageSelector = ({
const
listMapWithChildrenAndDescendants
=
list
.
reduce
((
prev
:
NotionPageTreeMap
,
next
:
DataSourceNotionPage
)
=>
{
const
pageId
=
next
.
page_id
if
(
!
prev
[
pageId
])
prev
[
pageId
]
=
{
...
next
,
children
:
new
Set
(),
descendants
:
new
Set
(),
deepth
:
0
}
prev
[
pageId
]
=
{
...
next
,
children
:
new
Set
(),
descendants
:
new
Set
(),
deepth
:
0
,
ancestors
:
[]
}
recursivePushInParentDescendants
(
listMap
,
prev
,
prev
[
pageId
],
prev
[
pageId
])
return
prev
...
...
@@ -176,18 +210,24 @@ const PageSelector = ({
}
const
handleCheck
=
(
index
:
number
)
=>
{
const
current
=
dataList
[
index
]
const
current
=
searchValue
?
searchDataList
[
index
]
:
dataList
[
index
]
const
pageId
=
current
.
page_id
const
currentWithChildrenAndDescendants
=
listMapWithChildrenAndDescendants
[
pageId
]
if
(
checkedIds
.
has
(
pageId
))
{
for
(
const
item
of
currentWithChildrenAndDescendants
.
descendants
)
checkedIds
.
delete
(
item
)
if
(
!
searchValue
)
{
for
(
const
item
of
currentWithChildrenAndDescendants
.
descendants
)
checkedIds
.
delete
(
item
)
}
checkedIds
.
delete
(
pageId
)
}
else
{
for
(
const
item
of
currentWithChildrenAndDescendants
.
descendants
)
checkedIds
.
add
(
item
)
if
(
!
searchValue
)
{
for
(
const
item
of
currentWithChildrenAndDescendants
.
descendants
)
checkedIds
.
add
(
item
)
}
checkedIds
.
add
(
pageId
)
}
...
...
@@ -203,20 +243,35 @@ const PageSelector = ({
}
}
useEffect
(()
=>
{
setSearchDataList
(
list
.
filter
((
item
)
=>
{
return
item
.
page_name
.
includes
(
searchValue
)
}).
map
((
item
)
=>
{
return
{
...
item
,
expand
:
false
,
deepth
:
0
,
}
}))
},
[
searchValue
])
return
(
<
List
className=
'py-2'
height=
{
296
}
itemCount=
{
dataList
.
length
}
itemCount=
{
searchValue
?
searchDataList
.
length
:
dataList
.
length
}
itemSize=
{
28
}
width=
'100%'
itemKey=
{
(
index
,
data
)
=>
data
.
dataList
[
index
].
page_id
}
itemData=
{
{
dataList
,
dataList
:
searchValue
?
searchDataList
:
dataList
,
handleToggle
,
checkedIds
,
handleCheck
,
canPreview
,
handlePreview
,
listMapWithChildrenAndDescendants
,
searchValue
,
}
}
>
{
Item
}
...
...
web/app/components/base/notion-page-selector/search-input/index.module.css
View file @
1ee00cba
...
...
@@ -9,5 +9,7 @@
}
.input-wrapper
{
flex-basis
:
200px
;
width
:
0
;
box-shadow
:
0px
1px
2px
rgba
(
16
,
24
,
40
,
0.05
);
}
\ No newline at end of file
web/app/components/base/notion-page-selector/search-input/index.tsx
View file @
1ee00cba
...
...
@@ -19,7 +19,7 @@ const SearchInput = ({
},
[])
return
(
<
div
className=
{
cn
(
s
[
'input-wrapper'
],
'flex items-center px-2
w-50
h-7 border border-gray-300 rounded-md'
,
`${value ? 'bg-white' : 'bg-gray-100'}`
)
}
>
<
div
className=
{
cn
(
s
[
'input-wrapper'
],
'flex items-center px-2 h-7 border border-gray-300 rounded-md'
,
`${value ? 'bg-white' : 'bg-gray-100'}`
)
}
>
<
div
className=
{
cn
(
s
[
'search-icon'
],
'mr-[6px] w-4 h-4'
)
}
/>
<
input
className=
'grow text-[13px] bg-inherit border-0 outline-0 appearance-none'
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment