From de15f8e2d3264b9ffb18c3a089612ef604eb87b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E3=81=8B=E3=81=A3=E3=81=93=E3=81=8B=E3=82=8A?= <67428053+kakkokari-gtyih@users.noreply.github.com> Date: Thu, 12 Dec 2024 01:31:29 +0900 Subject: [PATCH 01/12] feat(embed): Add support for dark mode (#6912) * feat(embed): Support dark mode (wip) * finishing up the implementation * fix tailwind color selector * tweak design * refactor: unify types * fix * fix english grammar * refactor: unify types * tweak design * remove the customization part --- bskyembed/snippet/embed.ts | 4 ++- bskyembed/src/color-mode.ts | 17 +++++++++++++ bskyembed/src/components/container.tsx | 2 +- bskyembed/src/components/embed.tsx | 34 +++++++++++++++----------- bskyembed/src/components/post.tsx | 18 ++++++++------ bskyembed/src/index.css | 4 +++ bskyembed/src/screens/landing.tsx | 31 +++++++++++++---------- bskyembed/src/screens/post.tsx | 9 ++++--- bskyembed/tailwind.config.cjs | 8 ++++++ bskyembed/tsconfig.json | 3 +-- 10 files changed, 88 insertions(+), 42 deletions(-) create mode 100644 bskyembed/src/color-mode.ts diff --git a/bskyembed/snippet/embed.ts b/bskyembed/snippet/embed.ts index 380cda5fb9..3c1b14b955 100644 --- a/bskyembed/snippet/embed.ts +++ b/bskyembed/snippet/embed.ts @@ -20,6 +20,7 @@ window.addEventListener('message', event => { return } + // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment const id = (event.data as {id: string}).id if (!id) { return @@ -33,6 +34,7 @@ window.addEventListener('message', event => { return } + // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment const height = (event.data as {height: number}).height if (height) { embed.style.height = `${height}px` @@ -47,7 +49,7 @@ window.addEventListener('message', event => { * @returns */ function scan(node = document) { - const embeds = node.querySelectorAll('[data-bluesky-uri]') + const embeds = node.querySelectorAll('[data-bluesky-uri]') for (let i = 0; i < embeds.length; i++) { const id = String(Math.random()).slice(2) diff --git a/bskyembed/src/color-mode.ts b/bskyembed/src/color-mode.ts new file mode 100644 index 0000000000..2b392c6178 --- /dev/null +++ b/bskyembed/src/color-mode.ts @@ -0,0 +1,17 @@ +export function applyTheme(theme: 'light' | 'dark') { + document.documentElement.classList.remove('light', 'dark') + document.documentElement.classList.add(theme) +} + +export function initColorMode() { + applyTheme( + window.matchMedia('(prefers-color-scheme: dark)').matches + ? 'dark' + : 'light', + ) + window + .matchMedia('(prefers-color-scheme: dark)') + .addEventListener('change', mql => { + applyTheme(mql.matches ? 'dark' : 'light') + }) +} diff --git a/bskyembed/src/components/container.tsx b/bskyembed/src/components/container.tsx index 5b1b2b7fb4..8e142a25be 100644 --- a/bskyembed/src/components/container.tsx +++ b/bskyembed/src/components/container.tsx @@ -37,7 +37,7 @@ export function Container({ return (
{ if (ref.current && href) { // forwardRef requires preact/compat - let's keep it simple diff --git a/bskyembed/src/components/embed.tsx b/bskyembed/src/components/embed.tsx index 74eacf16d4..20ffcb2b29 100644 --- a/bskyembed/src/components/embed.tsx +++ b/bskyembed/src/components/embed.tsx @@ -78,9 +78,9 @@ export function Embed({ return ( + className="transition-colors hover:bg-neutral-100 dark:hover:bg-slate-700 border dark:border-slate-600 rounded-lg p-2 gap-1.5 w-full flex flex-col">
-
+

{record.author.displayName} - + @{record.author.handle}

@@ -209,7 +209,7 @@ function Info({children}: {children: ComponentChildren}) { return (
-

{children}

+

{children}

) } @@ -308,7 +308,7 @@ function ExternalEmbed({ return ( {content.external.thumb && ( )}
-

+

{toNiceDomain(content.external.uri)}

{content.external.title}

-

+

{content.external.description}

@@ -345,23 +345,29 @@ function GenericWithImageEmbed({ return ( + className="w-full rounded-lg border dark:border-slate-600 py-2 px-3 flex flex-col gap-2">
{image ? ( {title} ) : (
)}

{title}

-

{subtitle}

+

+ {subtitle} +

- {description &&

{description}

} + {description && ( +

+ {description} +

+ )} ) } @@ -406,7 +412,7 @@ function StarterPackEmbed({ return ( + className="w-full rounded-lg overflow-hidden border dark:border-slate-600 flex flex-col items-stretch">
@@ -415,7 +421,7 @@ function StarterPackEmbed({

{content.record.name}

-

+

Starter pack by{' '} {content.creator.displayName || `@${content.creator.handle}`}

@@ -425,7 +431,7 @@ function StarterPackEmbed({

{content.record.description}

)} {!!content.joinedAllTimeCount && content.joinedAllTimeCount > 50 && ( -

+

{content.joinedAllTimeCount} users have joined!

)} diff --git a/bskyembed/src/components/post.tsx b/bskyembed/src/components/post.tsx index 4db5eeb45e..26945eb69d 100644 --- a/bskyembed/src/components/post.tsx +++ b/bskyembed/src/components/post.tsx @@ -38,7 +38,7 @@ export function Post({thread}: Props) {
-
+
+ className="text-[15px] text-textLight dark:text-textDimmed hover:underline line-clamp-1">

@{post.author.handle}

@@ -69,15 +69,15 @@ export function Post({thread}: Props) { -
+
{!!post.likeCount && (
-

+

{prettyNumber(post.likeCount)}

@@ -85,17 +85,19 @@ export function Post({thread}: Props) { {!!post.repostCount && (
-

+

{prettyNumber(post.repostCount)}

)}
-

Reply

+

+ Reply +

-

+

{post.replyCount ? `Read ${prettyNumber(post.replyCount)} ${ post.replyCount > 1 ? 'replies' : 'reply' diff --git a/bskyembed/src/index.css b/bskyembed/src/index.css index 22b2b8be5c..289e34cf00 100644 --- a/bskyembed/src/index.css +++ b/bskyembed/src/index.css @@ -5,3 +5,7 @@ .break-word { word-break: break-word; } + +:root { + color-scheme: light dark; +} diff --git a/bskyembed/src/screens/landing.tsx b/bskyembed/src/screens/landing.tsx index a9e08cd3f2..a3448e90ac 100644 --- a/bskyembed/src/screens/landing.tsx +++ b/bskyembed/src/screens/landing.tsx @@ -6,6 +6,7 @@ import {useEffect, useMemo, useRef, useState} from 'preact/hooks' import arrowBottom from '../../assets/arrowBottom_stroke2_corner0_rounded.svg' import logo from '../../assets/logo.svg' +import {initColorMode} from '../color-mode' import {Container} from '../components/container' import {Link} from '../components/link' import {Post} from '../components/post' @@ -21,6 +22,8 @@ export const EMBED_SCRIPT = `${EMBED_SERVICE}/static/embed.js` const root = document.getElementById('app') if (!root) throw new Error('No root element') +initColorMode() + const agent = new BskyAgent({ service: 'https://public.api.bsky.app', }) @@ -108,7 +111,7 @@ function LandingPage() { }, [uri]) return ( -

+
@@ -121,20 +124,22 @@ function LandingPage() { type="text" value={uri} onInput={e => setUri(e.currentTarget.value)} - className="border rounded-lg py-3 w-full max-w-[600px] px-4" + className="border rounded-lg py-3 w-full max-w-[600px] px-4 dark:bg-dimmedBg dark:border-slate-500" placeholder={DEFAULT_POST} /> - + {loading ? ( - +
+ +
) : (
{!error && thread && uri && } {!error && thread && } {error && ( -
+

{error}

)} @@ -149,15 +154,15 @@ function Skeleton() {
-
+
-
-
+
+
-
-
-
+
+
+
) @@ -220,7 +225,7 @@ function Snippet({thread}: {thread: AppBskyFeedDefs.ThreadViewPost}) { ref={ref} type="text" value={snippet} - className="border rounded-lg py-3 w-full px-4" + className="border rounded-lg py-3 w-full px-4 dark:bg-dimmedBg dark:border-slate-500" readOnly autoFocus onFocus={() => { @@ -228,7 +233,7 @@ function Snippet({thread}: {thread: AppBskyFeedDefs.ThreadViewPost}) { }} /> diff --git a/src/screens/Profile/Header/ProfileHeaderLabeler.tsx b/src/screens/Profile/Header/ProfileHeaderLabeler.tsx index ca0cb1e626..1725c4aaca 100644 --- a/src/screens/Profile/Header/ProfileHeaderLabeler.tsx +++ b/src/screens/Profile/Header/ProfileHeaderLabeler.tsx @@ -291,10 +291,12 @@ let ProfileHeaderLabeler = ({ }, }} size="tiny" - label={plural(likeCount, { - one: 'Liked by # user', - other: 'Liked by # users', - })}> + label={_( + msg`Liked by ${plural(likeCount, { + one: '# user', + other: '# users', + })}`, + )}> {({hovered, focused, pressed}) => ( - + + Liked by{' '} + + )} diff --git a/src/view/com/feeds/FeedSourceCard.tsx b/src/view/com/feeds/FeedSourceCard.tsx index 707aad7fb0..a591488891 100644 --- a/src/view/com/feeds/FeedSourceCard.tsx +++ b/src/view/com/feeds/FeedSourceCard.tsx @@ -300,11 +300,14 @@ export function FeedSourceCardLoaded({ {showLikes && feed.type === 'feed' ? ( - + + Liked by{' '} + + ) : null} diff --git a/src/view/com/util/post-ctrls/PostCtrls.tsx b/src/view/com/util/post-ctrls/PostCtrls.tsx index deb4b51d82..39caaf0987 100644 --- a/src/view/com/util/post-ctrls/PostCtrls.tsx +++ b/src/view/com/util/post-ctrls/PostCtrls.tsx @@ -258,10 +258,12 @@ let PostCtrls = ({ } }} accessibilityRole="button" - accessibilityLabel={plural(post.replyCount || 0, { - one: 'Reply (# reply)', - other: 'Reply (# replies)', - })} + accessibilityLabel={_( + msg`Reply (${plural(post.replyCount || 0, { + one: '# reply', + other: '# replies', + })})`, + )} accessibilityHint="" hitSlop={POST_CTRL_HITSLOP}> diff --git a/src/view/com/util/post-ctrls/RepostButton.tsx b/src/view/com/util/post-ctrls/RepostButton.tsx index 06b1fcaf6b..ca1647a991 100644 --- a/src/view/com/util/post-ctrls/RepostButton.tsx +++ b/src/view/com/util/post-ctrls/RepostButton.tsx @@ -62,11 +62,21 @@ let RepostButton = ({ {padding: 5}, ]} hoverStyle={t.atoms.bg_contrast_25} - label={`${ + label={ isReposted - ? _(msg`Undo repost`) - : _(msg({message: 'Repost', context: 'action'})) - } (${plural(repostCount || 0, {one: '# repost', other: '# reposts'})})`} + ? _( + msg`Undo repost (${plural(repostCount || 0, { + one: '# repost', + other: '# reposts', + })})`, + ) + : _( + msg`Repost (${plural(repostCount || 0, { + one: '# repost', + other: '# reposts', + })})`, + ) + } shape="round" variant="ghost" color="secondary" diff --git a/src/view/screens/ProfileFeed.tsx b/src/view/screens/ProfileFeed.tsx index dd2f8f12b5..c3f98c067f 100644 --- a/src/view/screens/ProfileFeed.tsx +++ b/src/view/screens/ProfileFeed.tsx @@ -587,11 +587,9 @@ function AboutSection({ label={_(msg`View users who like this feed`)} to={makeCustomFeedLink(feedOwnerDid, feedRkey, 'liked-by')} style={[t.atoms.text_contrast_medium, a.font_bold]}> - + + Liked by + )} From c8745a9ab0a99ac3cf484e00760e72d1e9f28dfc Mon Sep 17 00:00:00 2001 From: dan Date: Thu, 12 Dec 2024 04:20:22 +0000 Subject: [PATCH 10/12] Cache Reanimated worklets (#7068) * Undo perf hackfix * Bump Reanimated to include https://github.com/software-mansion/react-native-reanimated/pull/6758 * Bump to 3.17.0-nightly-20241211-17e89ca24 --- package.json | 2 +- src/view/com/util/MainScrollProvider.tsx | 25 ++++++------------------ yarn.lock | 8 ++++---- 3 files changed, 11 insertions(+), 24 deletions(-) diff --git a/package.json b/package.json index 4c7c179693..79735a1936 100644 --- a/package.json +++ b/package.json @@ -181,7 +181,7 @@ "react-native-picker-select": "^9.3.1", "react-native-progress": "bluesky-social/react-native-progress", "react-native-qrcode-styled": "^0.3.3", - "react-native-reanimated": "^3.16.3", + "react-native-reanimated": "3.17.0-nightly-20241211-17e89ca24", "react-native-root-siblings": "^4.1.1", "react-native-safe-area-context": "4.14.0", "react-native-screens": "~4.3.0", diff --git a/src/view/com/util/MainScrollProvider.tsx b/src/view/com/util/MainScrollProvider.tsx index c1293a83c0..e2538eaab6 100644 --- a/src/view/com/util/MainScrollProvider.tsx +++ b/src/view/com/util/MainScrollProvider.tsx @@ -1,11 +1,6 @@ import React, {useCallback, useEffect} from 'react' import {NativeScrollEvent} from 'react-native' -import { - interpolate, - makeMutable, - useSharedValue, - withSpring, -} from 'react-native-reanimated' +import {interpolate, useSharedValue, withSpring} from 'react-native-reanimated' import EventEmitter from 'eventemitter3' import {ScrollProvider} from '#/lib/ScrollContext' @@ -20,18 +15,6 @@ function clamp(num: number, min: number, max: number) { return Math.min(Math.max(num, min), max) } -const V0 = makeMutable( - withSpring(0, { - overshootClamping: true, - }), -) - -const V1 = makeMutable( - withSpring(1, { - overshootClamping: true, - }), -) - export function MainScrollProvider({children}: {children: React.ReactNode}) { const {headerHeight} = useShellLayout() const {headerMode} = useMinimalShellMode() @@ -42,7 +25,11 @@ export function MainScrollProvider({children}: {children: React.ReactNode}) { const setMode = React.useCallback( (v: boolean) => { 'worklet' - headerMode.set(v ? V1.get() : V0.get()) + headerMode.set(() => + withSpring(v ? 1 : 0, { + overshootClamping: true, + }), + ) }, [headerMode], ) diff --git a/yarn.lock b/yarn.lock index 21fdb48c60..03ffcfcfd6 100644 --- a/yarn.lock +++ b/yarn.lock @@ -16047,10 +16047,10 @@ react-native-qrcode-styled@^0.3.3: qrcode "^1.5.4" react-fast-compare "^3.2.2" -react-native-reanimated@^3.16.3: - version "3.16.3" - resolved "https://registry.yarnpkg.com/react-native-reanimated/-/react-native-reanimated-3.16.3.tgz#3b559dca49e9e40abcf5de834dc27fc05f856b66" - integrity sha512-OWlA6e1oHhytTpc7WiSZ7Tmb8OYwLKYZz29Sz6d6WAg60Hm5GuAiKIWUG7Ako7FLcYhFkA0pEQ2xPMEYUo9vlw== +react-native-reanimated@3.17.0-nightly-20241211-17e89ca24: + version "3.17.0-nightly-20241211-17e89ca24" + resolved "https://registry.yarnpkg.com/react-native-reanimated/-/react-native-reanimated-3.17.0-nightly-20241211-17e89ca24.tgz#af0c36e278646eb2f79e28ad0047cfd80d0e29f5" + integrity sha512-5p7jr0DrnID1puOzMel3VZVRw5Hl/UdMUvPCI1sEG9IA2mUaWrgeoojS2wVwW1U0Pj6HXjPNEimDSXZneZKNuQ== dependencies: "@babel/plugin-transform-arrow-functions" "^7.0.0-0" "@babel/plugin-transform-class-properties" "^7.0.0-0" From 20ac42a5a324ad553324d15ad868a1fea1868641 Mon Sep 17 00:00:00 2001 From: Snow Pettersen Date: Wed, 11 Dec 2024 20:28:15 -0800 Subject: [PATCH 11/12] configure the bitdrift Capture SDK (#6979) * configure bitdrift Capture SDK * remove console log * use the new url * add patch to fix devtool interaction * update patches * fix patch * add BITDRIFT_API_KEY to .env.example --- .env.example | 1 + app.config.js | 1 + docs/build.md | 6 ++++++ package.json | 1 + patches/expo-modules-core+2.1.1.md | 3 +++ patches/expo-modules-core+2.1.1.patch | 15 +++++++++++++++ src/App.native.tsx | 1 + src/lib/bitdrift.ts | 7 +++++++ src/logger/index.ts | 24 ++++++++++++++++++++++++ yarn.lock | 5 +++++ 10 files changed, 64 insertions(+) create mode 100644 patches/expo-modules-core+2.1.1.md create mode 100644 patches/expo-modules-core+2.1.1.patch create mode 100644 src/lib/bitdrift.ts diff --git a/.env.example b/.env.example index 6ab02256e4..979589f58b 100644 --- a/.env.example +++ b/.env.example @@ -1,5 +1,6 @@ # Copy this to `.env` and `.env.test` files +BITDRIFT_API_KEY= SENTRY_AUTH_TOKEN= EXPO_PUBLIC_ENV=development EXPO_PUBLIC_LOG_LEVEL=debug diff --git a/app.config.js b/app.config.js index 8b288e1a73..bc283152bd 100644 --- a/app.config.js +++ b/app.config.js @@ -222,6 +222,7 @@ module.exports = function (config) { }, ], 'react-native-compressor', + '@bitdrift/react-native', './plugins/starterPackAppClipExtension/withStarterPackAppClip.js', './plugins/withAndroidManifestPlugin.js', './plugins/withAndroidManifestFCMIconPlugin.js', diff --git a/docs/build.md b/docs/build.md index 6661d8fb21..7a29ab3553 100644 --- a/docs/build.md +++ b/docs/build.md @@ -87,6 +87,12 @@ However, if you're a part of the Bluesky team and want to enable Sentry, fill in If you change `SENTRY_AUTH_TOKEN`, you need to do `yarn prebuild` before running `yarn ios` or `yarn android` again. +### Adding bitdrift + +Adding bitdirft is NOT required. You can keep `BITDRIFT_API_KEY=` in `.env` which will avoid initializing bitdrift during startup. + +However, if you're a part of the Bluesky team and want to enable bitdrift, fill in `BITDRIFT_API_KEY` in your `.env` to enable bitdrift. + ### Adding and Updating Locales - `yarn intl:build` -> you will also need to run this anytime `./src/locale/{locale}/messages.po` change diff --git a/package.json b/package.json index 79735a1936..bbe46aa7c3 100644 --- a/package.json +++ b/package.json @@ -55,6 +55,7 @@ }, "dependencies": { "@atproto/api": "^0.13.18", + "@bitdrift/react-native": "0.4.0", "@braintree/sanitize-url": "^6.0.2", "@discord/bottom-sheet": "bluesky-social/react-native-bottom-sheet", "@emoji-mart/react": "^1.1.1", diff --git a/patches/expo-modules-core+2.1.1.md b/patches/expo-modules-core+2.1.1.md new file mode 100644 index 0000000000..a71324c19e --- /dev/null +++ b/patches/expo-modules-core+2.1.1.md @@ -0,0 +1,3 @@ +## expo-modules-core Patch + +This patch fixes an issue where bitdrift's API stream gets blocked by the Expo interceptor used to power the devtools diff --git a/patches/expo-modules-core+2.1.1.patch b/patches/expo-modules-core+2.1.1.patch new file mode 100644 index 0000000000..f3d9bfd149 --- /dev/null +++ b/patches/expo-modules-core+2.1.1.patch @@ -0,0 +1,15 @@ +diff --git a/node_modules/expo-modules-core/android/src/main/java/expo/modules/kotlin/devtools/ExpoNetworkInspectOkHttpInterceptors.kt b/node_modules/expo-modules-core/android/src/main/java/expo/modules/kotlin/devtools/ExpoNetworkInspectOkHttpInterceptors.kt +index 47c4d15..afe138d 100644 +--- a/node_modules/expo-modules-core/android/src/main/java/expo/modules/kotlin/devtools/ExpoNetworkInspectOkHttpInterceptors.kt ++++ b/node_modules/expo-modules-core/android/src/main/java/expo/modules/kotlin/devtools/ExpoNetworkInspectOkHttpInterceptors.kt +@@ -125,6 +125,10 @@ internal fun peekResponseBody( + } + + internal fun shouldParseBody(response: Response): Boolean { ++ if (response.request.url.encodedPath == "/bitdrift_public.protobuf.client.v1.ApiService/Mux") { ++ return false ++ } ++ + // Check for Content-Type + val skipContentTypes = listOf( + "text/event-stream", // Server Sent Events diff --git a/src/App.native.tsx b/src/App.native.tsx index 0d8d7a92e6..bc38eec799 100644 --- a/src/App.native.tsx +++ b/src/App.native.tsx @@ -1,5 +1,6 @@ import 'react-native-url-polyfill/auto' import '#/lib/sentry' // must be near top +import '#/lib/bitdrift' // must be near top import '#/view/icons' import React, {useEffect, useState} from 'react' diff --git a/src/lib/bitdrift.ts b/src/lib/bitdrift.ts new file mode 100644 index 0000000000..2b22155e78 --- /dev/null +++ b/src/lib/bitdrift.ts @@ -0,0 +1,7 @@ +import {init} from '@bitdrift/react-native' + +const BITDRIFT_API_KEY = process.env.BITDRIFT_API_KEY + +if (BITDRIFT_API_KEY) { + init(BITDRIFT_API_KEY, {url: 'https://api-bsky.bitdrift.io'}) +} diff --git a/src/logger/index.ts b/src/logger/index.ts index 7bd812af00..e4adc48e28 100644 --- a/src/logger/index.ts +++ b/src/logger/index.ts @@ -1,3 +1,9 @@ +import { + debug as bdDebug, + error as bdError, + info as bdInfo, + warn as bdWarn, +} from '@bitdrift/react-native' import format from 'date-fns/format' import {nanoid} from 'nanoid/non-secure' @@ -131,6 +137,20 @@ export const consoleTransport: Transport = ( } } +export const bitdriftTransport: Transport = (level, message) => { + const log = ( + { + [LogLevel.Debug]: bdDebug, + [LogLevel.Info]: bdInfo, + [LogLevel.Log]: bdInfo, + [LogLevel.Warn]: bdWarn, + [LogLevel.Error]: bdError, + } as const + )[level] + + log(message.toString()) +} + export const sentryTransport: Transport = ( level, message, @@ -328,6 +348,10 @@ export class Logger { */ export const logger = new Logger() +if (!env.IS_TEST) { + logger.addTransport(bitdriftTransport) +} + if (env.IS_DEV && !env.IS_TEST) { logger.addTransport(consoleTransport) diff --git a/yarn.lock b/yarn.lock index 03ffcfcfd6..16fe9579a4 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3377,6 +3377,11 @@ resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39" integrity sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw== +"@bitdrift/react-native@0.4.0": + version "0.4.0" + resolved "https://registry.yarnpkg.com/@bitdrift/react-native/-/react-native-0.4.0.tgz#e6484343ef04824aa924df2a757bd9620b2106c1" + integrity sha512-KuYzWEkoGwjjP0ZurjHwV+zfRZjQXxbXa3zhijWv0iqzMI/7kbrBd9lm+wNQo8OrkqFVDlebCb8AGPc0jMZw7A== + "@braintree/sanitize-url@^6.0.2": version "6.0.4" resolved "https://registry.yarnpkg.com/@braintree/sanitize-url/-/sanitize-url-6.0.4.tgz#923ca57e173c6b232bbbb07347b1be982f03e783" From 704e36c2801c4c06a3763eaef90c6a3e532a326d Mon Sep 17 00:00:00 2001 From: dan Date: Thu, 12 Dec 2024 05:00:09 +0000 Subject: [PATCH 12/12] Fix web build (#7069) * Fix web build * Fix circular deps * Hoist log functions --- src/logger/bitdriftTransport.ts | 23 +++++++ src/logger/bitdriftTransport.web.ts | 7 +++ src/logger/index.ts | 94 ++--------------------------- src/logger/types.ts | 69 +++++++++++++++++++++ 4 files changed, 105 insertions(+), 88 deletions(-) create mode 100644 src/logger/bitdriftTransport.ts create mode 100644 src/logger/bitdriftTransport.web.ts create mode 100644 src/logger/types.ts diff --git a/src/logger/bitdriftTransport.ts b/src/logger/bitdriftTransport.ts new file mode 100644 index 0000000000..c2235e0d4b --- /dev/null +++ b/src/logger/bitdriftTransport.ts @@ -0,0 +1,23 @@ +import { + debug as bdDebug, + error as bdError, + info as bdInfo, + warn as bdWarn, +} from '@bitdrift/react-native' + +import {LogLevel, Transport} from './types' + +export function createBitdriftTransport(): Transport { + const logFunctions = { + [LogLevel.Debug]: bdDebug, + [LogLevel.Info]: bdInfo, + [LogLevel.Log]: bdInfo, + [LogLevel.Warn]: bdWarn, + [LogLevel.Error]: bdError, + } as const + + return (level, message) => { + const log = logFunctions[level] + log(message.toString()) + } +} diff --git a/src/logger/bitdriftTransport.web.ts b/src/logger/bitdriftTransport.web.ts new file mode 100644 index 0000000000..ecea3f6f3b --- /dev/null +++ b/src/logger/bitdriftTransport.web.ts @@ -0,0 +1,7 @@ +import {Transport} from './index' + +export function createBitdriftTransport(): Transport { + return (_level, _message) => { + // noop + } +} diff --git a/src/logger/index.ts b/src/logger/index.ts index e4adc48e28..02e5d5f257 100644 --- a/src/logger/index.ts +++ b/src/logger/index.ts @@ -1,9 +1,3 @@ -import { - debug as bdDebug, - error as bdError, - info as bdInfo, - warn as bdWarn, -} from '@bitdrift/react-native' import format from 'date-fns/format' import {nanoid} from 'nanoid/non-secure' @@ -12,74 +6,12 @@ import {DebugContext} from '#/logger/debugContext' import {add} from '#/logger/logDump' import {Sentry} from '#/logger/sentry' import * as env from '#/env' +import {createBitdriftTransport} from './bitdriftTransport' +import {Metadata} from './types' +import {ConsoleTransportEntry, LogLevel, Transport} from './types' -export enum LogLevel { - Debug = 'debug', - Info = 'info', - Log = 'log', - Warn = 'warn', - Error = 'error', -} - -type Transport = ( - level: LogLevel, - message: string | Error, - metadata: Metadata, - timestamp: number, -) => void - -/** - * A union of some of Sentry's breadcrumb properties as well as Sentry's - * `captureException` parameter, `CaptureContext`. - */ -type Metadata = { - /** - * Applied as Sentry breadcrumb types. Defaults to `default`. - * - * @see https://develop.sentry.dev/sdk/event-payloads/breadcrumbs/#breadcrumb-types - */ - type?: - | 'default' - | 'debug' - | 'error' - | 'navigation' - | 'http' - | 'info' - | 'query' - | 'transaction' - | 'ui' - | 'user' - - /** - * Passed through to `Sentry.captureException` - * - * @see https://github.com/getsentry/sentry-javascript/blob/903addf9a1a1534a6cb2ba3143654b918a86f6dd/packages/types/src/misc.ts#L65 - */ - tags?: { - [key: string]: - | number - | string - | boolean - | bigint - | symbol - | null - | undefined - } - - /** - * Any additional data, passed through to Sentry as `extra` param on - * exceptions, or the `data` param on breadcrumbs. - */ - [key: string]: unknown -} & Parameters[1] - -export type ConsoleTransportEntry = { - id: string - timestamp: number - level: LogLevel - message: string | Error - metadata: Metadata -} +export {LogLevel} +export type {ConsoleTransportEntry, Transport} const enabledLogLevels: { [key in LogLevel]: LogLevel[] @@ -137,20 +69,6 @@ export const consoleTransport: Transport = ( } } -export const bitdriftTransport: Transport = (level, message) => { - const log = ( - { - [LogLevel.Debug]: bdDebug, - [LogLevel.Info]: bdInfo, - [LogLevel.Log]: bdInfo, - [LogLevel.Warn]: bdWarn, - [LogLevel.Error]: bdError, - } as const - )[level] - - log(message.toString()) -} - export const sentryTransport: Transport = ( level, message, @@ -349,7 +267,7 @@ export class Logger { export const logger = new Logger() if (!env.IS_TEST) { - logger.addTransport(bitdriftTransport) + logger.addTransport(createBitdriftTransport()) } if (env.IS_DEV && !env.IS_TEST) { diff --git a/src/logger/types.ts b/src/logger/types.ts new file mode 100644 index 0000000000..252e7373be --- /dev/null +++ b/src/logger/types.ts @@ -0,0 +1,69 @@ +import type {Sentry} from '#/logger/sentry' + +export enum LogLevel { + Debug = 'debug', + Info = 'info', + Log = 'log', + Warn = 'warn', + Error = 'error', +} + +export type Transport = ( + level: LogLevel, + message: string | Error, + metadata: Metadata, + timestamp: number, +) => void + +/** + * A union of some of Sentry's breadcrumb properties as well as Sentry's + * `captureException` parameter, `CaptureContext`. + */ +export type Metadata = { + /** + * Applied as Sentry breadcrumb types. Defaults to `default`. + * + * @see https://develop.sentry.dev/sdk/event-payloads/breadcrumbs/#breadcrumb-types + */ + type?: + | 'default' + | 'debug' + | 'error' + | 'navigation' + | 'http' + | 'info' + | 'query' + | 'transaction' + | 'ui' + | 'user' + + /** + * Passed through to `Sentry.captureException` + * + * @see https://github.com/getsentry/sentry-javascript/blob/903addf9a1a1534a6cb2ba3143654b918a86f6dd/packages/types/src/misc.ts#L65 + */ + tags?: { + [key: string]: + | number + | string + | boolean + | bigint + | symbol + | null + | undefined + } + + /** + * Any additional data, passed through to Sentry as `extra` param on + * exceptions, or the `data` param on breadcrumbs. + */ + [key: string]: unknown +} & Parameters[1] + +export type ConsoleTransportEntry = { + id: string + timestamp: number + level: LogLevel + message: string | Error + metadata: Metadata +}