mirror of
https://github.com/d0zingcat/NotionNext.git
synced 2026-05-28 15:10:04 +00:00
Merge remote-tracking branch 'origin/feat/notion-page-link-convert' into release/4.5.2
This commit is contained in:
@@ -6,71 +6,12 @@ import TianLiGPT from './TianliGPT'
|
|||||||
import WebWhiz from './Webwhiz'
|
import WebWhiz from './Webwhiz'
|
||||||
|
|
||||||
import { CUSTOM_EXTERNAL_CSS, CUSTOM_EXTERNAL_JS } from '@/blog.config'
|
import { CUSTOM_EXTERNAL_CSS, CUSTOM_EXTERNAL_JS } from '@/blog.config'
|
||||||
|
import { mapPageUrl } from '@/lib/notion/mapPageUrl'
|
||||||
import { isBrowser, loadExternalResource } from '@/lib/utils'
|
import { isBrowser, loadExternalResource } from '@/lib/utils'
|
||||||
|
import { useRouter } from 'next/router'
|
||||||
import { useEffect } from 'react'
|
import { useEffect } from 'react'
|
||||||
import { initGoogleAdsense } from './GoogleAdsense'
|
import { initGoogleAdsense } from './GoogleAdsense'
|
||||||
|
|
||||||
const TwikooCommentCounter = dynamic(
|
|
||||||
() => import('@/components/TwikooCommentCounter'),
|
|
||||||
{ ssr: false }
|
|
||||||
)
|
|
||||||
const DebugPanel = dynamic(() => import('@/components/DebugPanel'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const ThemeSwitch = dynamic(() => import('@/components/ThemeSwitch'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const Fireworks = dynamic(() => import('@/components/Fireworks'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const MouseFollow = dynamic(() => import('@/components/MouseFollow'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const Nest = dynamic(() => import('@/components/Nest'), { ssr: false })
|
|
||||||
const FlutteringRibbon = dynamic(
|
|
||||||
() => import('@/components/FlutteringRibbon'),
|
|
||||||
{ ssr: false }
|
|
||||||
)
|
|
||||||
const Ribbon = dynamic(() => import('@/components/Ribbon'), { ssr: false })
|
|
||||||
const Sakura = dynamic(() => import('@/components/Sakura'), { ssr: false })
|
|
||||||
const StarrySky = dynamic(() => import('@/components/StarrySky'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const DifyChatbot = dynamic(() => import('@/components/DifyChatbot'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const Analytics = dynamic(
|
|
||||||
() =>
|
|
||||||
import('@vercel/analytics/react').then(async m => {
|
|
||||||
return m.Analytics
|
|
||||||
}),
|
|
||||||
{ ssr: false }
|
|
||||||
)
|
|
||||||
const MusicPlayer = dynamic(() => import('@/components/Player'), { ssr: false })
|
|
||||||
const Ackee = dynamic(() => import('@/components/Ackee'), { ssr: false })
|
|
||||||
const Gtag = dynamic(() => import('@/components/Gtag'), { ssr: false })
|
|
||||||
const Busuanzi = dynamic(() => import('@/components/Busuanzi'), { ssr: false })
|
|
||||||
const Messenger = dynamic(() => import('@/components/FacebookMessenger'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const VConsole = dynamic(() => import('@/components/VConsole'), { ssr: false })
|
|
||||||
const CustomContextMenu = dynamic(
|
|
||||||
() => import('@/components/CustomContextMenu'),
|
|
||||||
{ ssr: false }
|
|
||||||
)
|
|
||||||
const DisableCopy = dynamic(() => import('@/components/DisableCopy'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const AdBlockDetect = dynamic(() => import('@/components/AdBlockDetect'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const LoadingProgress = dynamic(() => import('@/components/LoadingProgress'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
const AosAnimation = dynamic(() => import('@/components/AOSAnimation'), {
|
|
||||||
ssr: false
|
|
||||||
})
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 各种插件脚本
|
* 各种插件脚本
|
||||||
* @param {*} props
|
* @param {*} props
|
||||||
@@ -155,6 +96,7 @@ const ExternalPlugin = props => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const router = useRouter()
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
// 异步渲染谷歌广告
|
// 异步渲染谷歌广告
|
||||||
if (ADSENSE_GOOGLE_ID) {
|
if (ADSENSE_GOOGLE_ID) {
|
||||||
@@ -163,6 +105,11 @@ const ExternalPlugin = props => {
|
|||||||
}, 1000)
|
}, 1000)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 映射url
|
||||||
|
mapPageUrl(props?.allNavPages)
|
||||||
|
}, [router])
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
// 执行注入脚本
|
// 执行注入脚本
|
||||||
// eslint-disable-next-line no-eval
|
// eslint-disable-next-line no-eval
|
||||||
eval(GLOBAL_JS)
|
eval(GLOBAL_JS)
|
||||||
@@ -389,4 +336,65 @@ const ExternalPlugin = props => {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const TwikooCommentCounter = dynamic(
|
||||||
|
() => import('@/components/TwikooCommentCounter'),
|
||||||
|
{ ssr: false }
|
||||||
|
)
|
||||||
|
const DebugPanel = dynamic(() => import('@/components/DebugPanel'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const ThemeSwitch = dynamic(() => import('@/components/ThemeSwitch'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const Fireworks = dynamic(() => import('@/components/Fireworks'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const MouseFollow = dynamic(() => import('@/components/MouseFollow'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const Nest = dynamic(() => import('@/components/Nest'), { ssr: false })
|
||||||
|
const FlutteringRibbon = dynamic(
|
||||||
|
() => import('@/components/FlutteringRibbon'),
|
||||||
|
{ ssr: false }
|
||||||
|
)
|
||||||
|
const Ribbon = dynamic(() => import('@/components/Ribbon'), { ssr: false })
|
||||||
|
const Sakura = dynamic(() => import('@/components/Sakura'), { ssr: false })
|
||||||
|
const StarrySky = dynamic(() => import('@/components/StarrySky'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const DifyChatbot = dynamic(() => import('@/components/DifyChatbot'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const Analytics = dynamic(
|
||||||
|
() =>
|
||||||
|
import('@vercel/analytics/react').then(async m => {
|
||||||
|
return m.Analytics
|
||||||
|
}),
|
||||||
|
{ ssr: false }
|
||||||
|
)
|
||||||
|
const MusicPlayer = dynamic(() => import('@/components/Player'), { ssr: false })
|
||||||
|
const Ackee = dynamic(() => import('@/components/Ackee'), { ssr: false })
|
||||||
|
const Gtag = dynamic(() => import('@/components/Gtag'), { ssr: false })
|
||||||
|
const Busuanzi = dynamic(() => import('@/components/Busuanzi'), { ssr: false })
|
||||||
|
const Messenger = dynamic(() => import('@/components/FacebookMessenger'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const VConsole = dynamic(() => import('@/components/VConsole'), { ssr: false })
|
||||||
|
const CustomContextMenu = dynamic(
|
||||||
|
() => import('@/components/CustomContextMenu'),
|
||||||
|
{ ssr: false }
|
||||||
|
)
|
||||||
|
const DisableCopy = dynamic(() => import('@/components/DisableCopy'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const AdBlockDetect = dynamic(() => import('@/components/AdBlockDetect'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const LoadingProgress = dynamic(() => import('@/components/LoadingProgress'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
const AosAnimation = dynamic(() => import('@/components/AOSAnimation'), {
|
||||||
|
ssr: false
|
||||||
|
})
|
||||||
|
|
||||||
export default ExternalPlugin
|
export default ExternalPlugin
|
||||||
|
|||||||
@@ -47,9 +47,6 @@ const NotionPage = ({ post, className }) => {
|
|||||||
processDisableDatabaseUrl()
|
processDisableDatabaseUrl()
|
||||||
}
|
}
|
||||||
|
|
||||||
// 若url是本站域名,则之间在当前窗口打开、不开新窗口
|
|
||||||
processPageUrl()
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 放大查看图片时替换成高清图像
|
* 放大查看图片时替换成高清图像
|
||||||
*/
|
*/
|
||||||
@@ -146,30 +143,6 @@ const processGalleryImg = zoom => {
|
|||||||
}, 800)
|
}, 800)
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 处理页面内连接跳转
|
|
||||||
* 如果链接就是当网站,则不打开新窗口访问
|
|
||||||
*/
|
|
||||||
const processPageUrl = () => {
|
|
||||||
if (isBrowser) {
|
|
||||||
const currentURL = window.location.origin + window.location.pathname
|
|
||||||
const allAnchorTags = document.getElementsByTagName('a') // 或者使用 document.querySelectorAll('a') 获取 NodeList
|
|
||||||
for (const anchorTag of allAnchorTags) {
|
|
||||||
if (anchorTag?.target === '_blank') {
|
|
||||||
const hrefWithoutQueryHash = anchorTag.href.split('?')[0].split('#')[0]
|
|
||||||
const hrefWithRelativeHash =
|
|
||||||
currentURL.split('#')[0] + anchorTag.href.split('#')[1]
|
|
||||||
|
|
||||||
if (
|
|
||||||
currentURL === hrefWithoutQueryHash ||
|
|
||||||
currentURL === hrefWithRelativeHash
|
|
||||||
) {
|
|
||||||
anchorTag.target = '_self'
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/**
|
/**
|
||||||
* 根据url参数自动滚动到指定区域
|
* 根据url参数自动滚动到指定区域
|
||||||
*/
|
*/
|
||||||
|
|||||||
40
lib/notion/mapPageUrl.js
Normal file
40
lib/notion/mapPageUrl.js
Normal file
@@ -0,0 +1,40 @@
|
|||||||
|
import { uuidToId } from 'notion-utils'
|
||||||
|
import { checkStrIsNotionId, getLastPartOfUrl, isBrowser } from '../utils'
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 处理页面内连接跳转:
|
||||||
|
* 1. 若是本站域名,则在当前窗口打开、不开新窗口
|
||||||
|
* 2. 若是Notion笔记中的内链,尝试转换成博客中现有的文章地址
|
||||||
|
*/
|
||||||
|
export const mapPageUrl = allPages => {
|
||||||
|
if (isBrowser) {
|
||||||
|
const currentURL = window.location.origin + window.location.pathname
|
||||||
|
const allAnchorTags = document.getElementsByTagName('a') // 或者使用 document.querySelectorAll('a') 获取 NodeList
|
||||||
|
for (const anchorTag of allAnchorTags) {
|
||||||
|
// 检查url
|
||||||
|
if (anchorTag?.href) {
|
||||||
|
// 如果url是一个Notion_id,尝试匹配成博客的文章内链
|
||||||
|
const slug = getLastPartOfUrl(anchorTag.href)
|
||||||
|
if (checkStrIsNotionId(slug)) {
|
||||||
|
const slugPage = allPages?.find(page => uuidToId(page.id) === slug)
|
||||||
|
if (slugPage) {
|
||||||
|
anchorTag.href = slugPage?.href
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (anchorTag?.target === '_blank') {
|
||||||
|
const hrefWithoutQueryHash = anchorTag.href.split('?')[0].split('#')[0]
|
||||||
|
const hrefWithRelativeHash =
|
||||||
|
currentURL.split('#')[0] + anchorTag.href.split('#')[1]
|
||||||
|
|
||||||
|
if (
|
||||||
|
currentURL === hrefWithoutQueryHash ||
|
||||||
|
currentURL === hrefWithRelativeHash
|
||||||
|
) {
|
||||||
|
anchorTag.target = '_self'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -93,6 +93,35 @@ export function checkContainHttp(str) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 检查一个字符串是否notionid : 32位,仅由数字英文构成
|
||||||
|
export function checkStrIsNotionId(str) {
|
||||||
|
if (!str) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
// 使用正则表达式进行匹配
|
||||||
|
const regex = /^[a-zA-Z0-9]{32}$/
|
||||||
|
return regex.test(str)
|
||||||
|
}
|
||||||
|
|
||||||
|
// 截取url中最后一个 / 后面的内容
|
||||||
|
export function getLastPartOfUrl(url) {
|
||||||
|
if (!url) {
|
||||||
|
return ''
|
||||||
|
}
|
||||||
|
// 找到最后一个斜杠的位置
|
||||||
|
const lastSlashIndex = url.lastIndexOf('/')
|
||||||
|
|
||||||
|
// 如果找不到斜杠,则返回整个字符串
|
||||||
|
if (lastSlashIndex === -1) {
|
||||||
|
return url
|
||||||
|
}
|
||||||
|
|
||||||
|
// 截取最后一个斜杠后面的内容
|
||||||
|
const lastPart = url.substring(lastSlashIndex + 1)
|
||||||
|
|
||||||
|
return lastPart
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 加载外部资源
|
* 加载外部资源
|
||||||
* @param url 地址 例如 https://xx.com/xx.js
|
* @param url 地址 例如 https://xx.com/xx.js
|
||||||
|
|||||||
Reference in New Issue
Block a user