diff --git a/src/lib/analytics/analytics.tsx b/src/lib/analytics/analytics.tsx index b3db9149..71bb8569 100644 --- a/src/lib/analytics/analytics.tsx +++ b/src/lib/analytics/analytics.tsx @@ -10,6 +10,7 @@ import {RootStoreModel, AppInfo} from 'state/models/root-store' import {useStores} from 'state/models/root-store' import {sha256} from 'js-sha256' import {ScreenEvent, TrackEvent} from './types' +import {logger} from '#/logger' const segmentClient = createClient({ writeKey: '8I6DsgfiSLuoONyaunGoiQM7A6y2ybdI', @@ -54,9 +55,9 @@ export function init(store: RootStoreModel) { if (sess.did) { const did_hashed = sha256(sess.did) segmentClient.identify(did_hashed, {did_hashed}) - store.log.debug('Ping w/hash') + logger.debug('Ping w/hash') } else { - store.log.debug('Ping w/o hash') + logger.debug('Ping w/o hash') segmentClient.identify() } } @@ -68,19 +69,19 @@ export function init(store: RootStoreModel) { // -prf segmentClient.isReady.onChange(() => { if (AppState.currentState !== 'active') { - store.log.debug('Prevented a metrics ping while the app was backgrounded') + logger.debug('Prevented a metrics ping while the app was backgrounded') return } const context = segmentClient.context.get() if (typeof context?.app === 'undefined') { - store.log.debug('Aborted metrics ping due to unavailable context') + logger.debug('Aborted metrics ping due to unavailable context') return } const oldAppInfo = store.appInfo const newAppInfo = context.app as AppInfo store.setAppInfo(newAppInfo) - store.log.debug('Recording app info', {new: newAppInfo, old: oldAppInfo}) + logger.debug('Recording app info', {new: newAppInfo, old: oldAppInfo}) if (typeof oldAppInfo === 'undefined') { if (store.session.hasSession) { diff --git a/src/lib/analytics/analytics.web.tsx b/src/lib/analytics/analytics.web.tsx index 78bd9b42..fe90d132 100644 --- a/src/lib/analytics/analytics.web.tsx +++ b/src/lib/analytics/analytics.web.tsx @@ -7,6 +7,7 @@ import { import {RootStoreModel} from 'state/models/root-store' import {useStores} from 'state/models/root-store' import {sha256} from 'js-sha256' +import {logger} from '#/logger' const segmentClient = createClient( { @@ -49,9 +50,9 @@ export function init(store: RootStoreModel) { if (sess.did) { const did_hashed = sha256(sess.did) segmentClient.identify(did_hashed, {did_hashed}) - store.log.debug('Ping w/hash') + logger.debug('Ping w/hash') } else { - store.log.debug('Ping w/o hash') + logger.debug('Ping w/o hash') segmentClient.identify() } } diff --git a/src/lib/api/index.ts b/src/lib/api/index.ts index f75ebbd9..9d48a78c 100644 --- a/src/lib/api/index.ts +++ b/src/lib/api/index.ts @@ -15,6 +15,7 @@ import {LinkMeta} from '../link-meta/link-meta' import {isWeb} from 'platform/detection' import {ImageModel} from 'state/models/media/image' import {shortenLinks} from 'lib/strings/rich-text-manip' +import {logger} from '#/logger' export interface ExternalEmbedDraft { uri: string @@ -178,7 +179,7 @@ export async function post(store: RootStoreModel, opts: PostOpts) { ) { encoding = 'image/jpeg' } else { - store.log.warn('Unexpected image format for thumbnail, skipping', { + logger.warn('Unexpected image format for thumbnail, skipping', { thumbnail: opts.extLink.localThumb.path, }) } diff --git a/src/lib/hooks/useFollowProfile.ts b/src/lib/hooks/useFollowProfile.ts index ca3f7ab8..98dd63f5 100644 --- a/src/lib/hooks/useFollowProfile.ts +++ b/src/lib/hooks/useFollowProfile.ts @@ -2,6 +2,7 @@ import React from 'react' import {AppBskyActorDefs} from '@atproto/api' import {useStores} from 'state/index' import {FollowState} from 'state/models/cache/my-follows' +import {logger} from '#/logger' export function useFollowProfile(profile: AppBskyActorDefs.ProfileViewBasic) { const store = useStores() @@ -22,7 +23,7 @@ export function useFollowProfile(profile: AppBskyActorDefs.ProfileViewBasic) { following: false, } } catch (e: any) { - store.log.error('Failed to delete follow', {error: e}) + logger.error('Failed to delete follow', {error: e}) throw e } } else if (state === FollowState.NotFollowing) { @@ -40,7 +41,7 @@ export function useFollowProfile(profile: AppBskyActorDefs.ProfileViewBasic) { following: true, } } catch (e: any) { - store.log.error('Failed to create follow', {error: e}) + logger.error('Failed to create follow', {error: e}) throw e } } diff --git a/src/lib/hooks/useOTAUpdate.ts b/src/lib/hooks/useOTAUpdate.ts index d7855b2d..0ce97a4c 100644 --- a/src/lib/hooks/useOTAUpdate.ts +++ b/src/lib/hooks/useOTAUpdate.ts @@ -2,6 +2,7 @@ import * as Updates from 'expo-updates' import {useCallback, useEffect} from 'react' import {AppState} from 'react-native' import {useStores} from 'state/index' +import {logger} from '#/logger' export function useOTAUpdate() { const store = useStores() @@ -21,7 +22,7 @@ export function useOTAUpdate() { }) }, [store.shell]) const checkForUpdate = useCallback(async () => { - store.log.debug('useOTAUpdate: Checking for update...') + logger.debug('useOTAUpdate: Checking for update...') try { // Check if new OTA update is available const update = await Updates.checkForUpdateAsync() @@ -34,16 +35,16 @@ export function useOTAUpdate() { // show a popup modal showUpdatePopup() } catch (e) { - store.log.error('useOTAUpdate: Error while checking for update', { + logger.error('useOTAUpdate: Error while checking for update', { error: e, }) } - }, [showUpdatePopup, store.log]) + }, [showUpdatePopup]) const updateEventListener = useCallback( (event: Updates.UpdateEvent) => { - store.log.debug('useOTAUpdate: Listening for update...') + logger.debug('useOTAUpdate: Listening for update...') if (event.type === Updates.UpdateEventType.ERROR) { - store.log.error('useOTAUpdate: Error while listening for update', { + logger.error('useOTAUpdate: Error while listening for update', { message: event.message, }) } else if (event.type === Updates.UpdateEventType.NO_UPDATE_AVAILABLE) { @@ -55,7 +56,7 @@ export function useOTAUpdate() { showUpdatePopup() } }, - [showUpdatePopup, store.log], + [showUpdatePopup], ) useEffect(() => { diff --git a/src/lib/notifications/notifications.ts b/src/lib/notifications/notifications.ts index 01b0ba93..73f9c56f 100644 --- a/src/lib/notifications/notifications.ts +++ b/src/lib/notifications/notifications.ts @@ -3,6 +3,7 @@ import {RootStoreModel} from '../../state' import {resetToTab} from '../../Navigation' import {devicePlatform, isIOS} from 'platform/detection' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' const SERVICE_DID = (serviceUrl?: string) => serviceUrl?.includes('staging') @@ -29,19 +30,27 @@ export function init(store: RootStoreModel) { token: token.data, appId: 'xyz.blueskyweb.app', }) - store.log.debug('Notifications: Sent push token (init)', { - tokenType: token.type, - token: token.data, - }) + logger.debug( + 'Notifications: Sent push token (init)', + { + tokenType: token.type, + token: token.data, + }, + logger.DebugContext.notifications, + ) } catch (error) { - store.log.error('Notifications: Failed to set push token', {error}) + logger.error('Notifications: Failed to set push token', {error}) } } // listens for new changes to the push token // In rare situations, a push token may be changed by the push notification service while the app is running. When a token is rolled, the old one becomes invalid and sending notifications to it will fail. A push token listener will let you handle this situation gracefully by registering the new token with your backend right away. Notifications.addPushTokenListener(async ({data: t, type}) => { - store.log.debug('Notifications: Push token changed', {t, tokenType: type}) + logger.debug( + 'Notifications: Push token changed', + {t, tokenType: type}, + logger.DebugContext.notifications, + ) if (t) { try { await store.agent.api.app.bsky.notification.registerPush({ @@ -50,12 +59,16 @@ export function init(store: RootStoreModel) { token: t, appId: 'xyz.blueskyweb.app', }) - store.log.debug('Notifications: Sent push token (event)', { - tokenType: type, - token: t, - }) + logger.debug( + 'Notifications: Sent push token (event)', + { + tokenType: type, + token: t, + }, + logger.DebugContext.notifications, + ) } catch (error) { - store.log.error('Notifications: Failed to set push token', {error}) + logger.error('Notifications: Failed to set push token', {error}) } } }) @@ -63,7 +76,11 @@ export function init(store: RootStoreModel) { // handle notifications that are received, both in the foreground or background Notifications.addNotificationReceivedListener(event => { - store.log.debug('Notifications: received', {event}) + logger.debug( + 'Notifications: received', + {event}, + logger.DebugContext.notifications, + ) if (event.request.trigger.type === 'push') { // refresh notifications in the background store.me.notifications.syncQueue() @@ -75,7 +92,11 @@ export function init(store: RootStoreModel) { // TODO: handle android payload deeplink } if (payload) { - store.log.debug('Notifications: received payload', payload) + logger.debug( + 'Notifications: received payload', + payload, + logger.DebugContext.notifications, + ) // TODO: deeplink notif here } } @@ -84,14 +105,20 @@ export function init(store: RootStoreModel) { // handle notifications that are tapped on const sub = Notifications.addNotificationResponseReceivedListener( response => { - store.log.debug('Notifications: response received', { - actionIdentifier: response.actionIdentifier, - }) + logger.debug( + 'Notifications: response received', + { + actionIdentifier: response.actionIdentifier, + }, + logger.DebugContext.notifications, + ) if ( response.actionIdentifier === Notifications.DEFAULT_ACTION_IDENTIFIER ) { - store.log.debug( + logger.debug( 'User pressed a notification, opening notifications tab', + {}, + logger.DebugContext.notifications, ) track('Notificatons:OpenApp') store.me.notifications.refresh() // refresh notifications diff --git a/src/logger/debugContext.ts b/src/logger/debugContext.ts index 658f4b18..0e04752e 100644 --- a/src/logger/debugContext.ts +++ b/src/logger/debugContext.ts @@ -7,4 +7,6 @@ */ export const DebugContext = { // e.g. composer: 'composer' + session: 'session', + notifications: 'notifications', } as const diff --git a/src/state/index.ts b/src/state/index.ts index 2c81c0dd..55dcae6d 100644 --- a/src/state/index.ts +++ b/src/state/index.ts @@ -4,6 +4,7 @@ import {BskyAgent} from '@atproto/api' import {RootStoreModel} from './models/root-store' import * as apiPolyfill from 'lib/api/api-polyfill' import * as storage from 'lib/storage' +import {logger} from '#/logger' export const LOCAL_DEV_SERVICE = Platform.OS === 'android' ? 'http://10.0.2.2:2583' : 'http://localhost:2583' @@ -22,10 +23,10 @@ export async function setupState(serviceUri = DEFAULT_SERVICE) { rootStore = new RootStoreModel(new BskyAgent({service: serviceUri})) try { data = (await storage.load(ROOT_STATE_STORAGE_KEY)) || {} - rootStore.log.debug('Initial hydrate', {hasSession: !!data.session}) + logger.debug('Initial hydrate', {hasSession: !!data.session}) rootStore.hydrate(data) } catch (e: any) { - rootStore.log.error('Failed to load state from storage', {error: e}) + logger.error('Failed to load state from storage', {error: e}) } rootStore.attemptSessionResumption() diff --git a/src/state/models/content/feed-source.ts b/src/state/models/content/feed-source.ts index d1b8fc9d..79747d6f 100644 --- a/src/state/models/content/feed-source.ts +++ b/src/state/models/content/feed-source.ts @@ -6,6 +6,7 @@ import {sanitizeHandle} from 'lib/strings/handles' import {bundleAsync} from 'lib/async/bundle' import {cleanError} from 'lib/strings/errors' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' export class FeedSourceModel { // state @@ -134,7 +135,7 @@ export class FeedSourceModel { try { await this.rootStore.preferences.addSavedFeed(this.uri) } catch (error) { - this.rootStore.log.error('Failed to save feed', {error}) + logger.error('Failed to save feed', {error}) } finally { track('CustomFeed:Save') } @@ -147,7 +148,7 @@ export class FeedSourceModel { try { await this.rootStore.preferences.removeSavedFeed(this.uri) } catch (error) { - this.rootStore.log.error('Failed to unsave feed', {error}) + logger.error('Failed to unsave feed', {error}) } finally { track('CustomFeed:Unsave') } @@ -157,7 +158,7 @@ export class FeedSourceModel { try { await this.rootStore.preferences.addPinnedFeed(this.uri) } catch (error) { - this.rootStore.log.error('Failed to pin feed', {error}) + logger.error('Failed to pin feed', {error}) } finally { track('CustomFeed:Pin', { name: this.displayName, @@ -194,7 +195,7 @@ export class FeedSourceModel { } catch (e: any) { this.likeUri = undefined this.likeCount = (this.likeCount || 1) - 1 - this.rootStore.log.error('Failed to like feed', {error: e}) + logger.error('Failed to like feed', {error: e}) } finally { track('CustomFeed:Like') } @@ -215,7 +216,7 @@ export class FeedSourceModel { } catch (e: any) { this.likeUri = uri this.likeCount = (this.likeCount || 0) + 1 - this.rootStore.log.error('Failed to unlike feed', {error: e}) + logger.error('Failed to unlike feed', {error: e}) } finally { track('CustomFeed:Unlike') } diff --git a/src/state/models/content/list.ts b/src/state/models/content/list.ts index 985d8d82..115426e5 100644 --- a/src/state/models/content/list.ts +++ b/src/state/models/content/list.ts @@ -16,6 +16,7 @@ import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' import {track} from 'lib/analytics/analytics' import {until} from 'lib/async/until' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -339,7 +340,7 @@ export class ListModel { try { await this.rootStore.preferences.addPinnedFeed(this.uri) } catch (error) { - this.rootStore.log.error('Failed to pin feed', {error}) + logger.error('Failed to pin feed', {error}) } finally { track('CustomFeed:Pin', { name: this.data?.name || '', @@ -455,10 +456,10 @@ export class ListModel { this.error = cleanError(err) this.loadMoreError = cleanError(loadMoreErr) if (err) { - this.rootStore.log.error('Failed to fetch user items', {error: err}) + logger.error('Failed to fetch user items', {error: err}) } if (loadMoreErr) { - this.rootStore.log.error('Failed to fetch user items', { + logger.error('Failed to fetch user items', { error: loadMoreErr, }) } diff --git a/src/state/models/content/post-thread.ts b/src/state/models/content/post-thread.ts index cf6377da..fd194056 100644 --- a/src/state/models/content/post-thread.ts +++ b/src/state/models/content/post-thread.ts @@ -11,6 +11,7 @@ import * as apilib from 'lib/api/index' import {cleanError} from 'lib/strings/errors' import {ThreadViewPreference} from '../ui/preferences' import {PostThreadItemModel} from './post-thread-item' +import {logger} from '#/logger' export class PostThreadModel { // state @@ -163,7 +164,7 @@ export class PostThreadModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch post thread', {error: err}) + logger.error('Failed to fetch post thread', {error: err}) } this.notFound = err instanceof GetPostThread.NotFoundError } diff --git a/src/state/models/content/profile.ts b/src/state/models/content/profile.ts index 0050970e..14362cee 100644 --- a/src/state/models/content/profile.ts +++ b/src/state/models/content/profile.ts @@ -15,6 +15,7 @@ import {cleanError} from 'lib/strings/errors' import {FollowState} from '../cache/my-follows' import {Image as RNImage} from 'react-native-image-crop-picker' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' export class ProfileViewerModel { muted?: boolean @@ -235,7 +236,7 @@ export class ProfileModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch profile', {error: err}) + logger.error('Failed to fetch profile', {error: err}) } } diff --git a/src/state/models/discovery/feeds.ts b/src/state/models/discovery/feeds.ts index 3902f3ac..a7c94e40 100644 --- a/src/state/models/discovery/feeds.ts +++ b/src/state/models/discovery/feeds.ts @@ -4,6 +4,7 @@ import {RootStoreModel} from '../root-store' import {bundleAsync} from 'lib/async/bundle' import {cleanError} from 'lib/strings/errors' import {FeedSourceModel} from '../content/feed-source' +import {logger} from '#/logger' const DEFAULT_LIMIT = 50 @@ -120,7 +121,7 @@ export class FeedsDiscoveryModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch popular feeds', {error: err}) + logger.error('Failed to fetch popular feeds', {error: err}) } } diff --git a/src/state/models/discovery/suggested-actors.ts b/src/state/models/discovery/suggested-actors.ts index 8776fcd8..450786c2 100644 --- a/src/state/models/discovery/suggested-actors.ts +++ b/src/state/models/discovery/suggested-actors.ts @@ -3,6 +3,7 @@ import {AppBskyActorDefs, moderateProfile} from '@atproto/api' import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -144,7 +145,7 @@ export class SuggestedActorsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch suggested actors', {error: err}) + logger.error('Failed to fetch suggested actors', {error: err}) } } } diff --git a/src/state/models/feeds/notifications.ts b/src/state/models/feeds/notifications.ts index a834b543..607e3038 100644 --- a/src/state/models/feeds/notifications.ts +++ b/src/state/models/feeds/notifications.ts @@ -17,6 +17,7 @@ import {bundleAsync} from 'lib/async/bundle' import {RootStoreModel} from '../root-store' import {PostThreadModel} from '../content/post-thread' import {cleanError} from 'lib/strings/errors' +import {logger} from '#/logger' const GROUPABLE_REASONS = ['like', 'repost', 'follow'] const PAGE_SIZE = 30 @@ -210,7 +211,7 @@ export class NotificationsFeedItemModel { if (valid.success) { return v } else { - this.rootStore.log.warn('Received an invalid record', { + logger.warn('Received an invalid record', { record: v, error: valid.error, }) @@ -218,7 +219,7 @@ export class NotificationsFeedItemModel { } } } - this.rootStore.log.warn( + logger.warn( 'app.bsky.notifications.list served an unsupported record type', {record: v}, ) @@ -319,7 +320,7 @@ export class NotificationsFeedModel { * Nuke all data */ clear() { - this.rootStore.log.debug('NotificationsModel:clear') + logger.debug('NotificationsModel:clear') this.isLoading = false this.isRefreshing = false this.hasLoaded = false @@ -336,7 +337,7 @@ export class NotificationsFeedModel { * Load for first render */ setup = bundleAsync(async (isRefreshing: boolean = false) => { - this.rootStore.log.debug('NotificationsModel:refresh', {isRefreshing}) + logger.debug('NotificationsModel:refresh', {isRefreshing}) await this.lock.acquireAsync() try { this._xLoading(isRefreshing) @@ -368,7 +369,7 @@ export class NotificationsFeedModel { * Sync the next set of notifications to show */ syncQueue = bundleAsync(async () => { - this.rootStore.log.debug('NotificationsModel:syncQueue') + logger.debug('NotificationsModel:syncQueue') if (this.unreadCount >= MAX_VISIBLE_NOTIFS) { return // no need to check } @@ -401,7 +402,7 @@ export class NotificationsFeedModel { this._setQueued(this._filterNotifications(queueModels)) this._countUnread() } catch (e) { - this.rootStore.log.error('NotificationsModel:syncQueue failed', { + logger.error('NotificationsModel:syncQueue failed', { error: e, }) } finally { @@ -463,10 +464,7 @@ export class NotificationsFeedModel { } } await Promise.all(promises).catch(e => { - this.rootStore.log.error( - 'Uncaught failure during notifications update()', - e, - ) + logger.error('Uncaught failure during notifications update()', e) }) } @@ -483,7 +481,7 @@ export class NotificationsFeedModel { this.lastSync ? this.lastSync.toISOString() : undefined, ) } catch (e: any) { - this.rootStore.log.warn('Failed to update notifications read state', { + logger.warn('Failed to update notifications read state', { error: e, }) } @@ -505,10 +503,10 @@ export class NotificationsFeedModel { this.error = cleanError(error) this.loadMoreError = cleanError(loadMoreError) if (error) { - this.rootStore.log.error('Failed to fetch notifications', {error}) + logger.error('Failed to fetch notifications', {error}) } if (loadMoreError) { - this.rootStore.log.error('Failed to load more notifications', { + logger.error('Failed to load more notifications', { error: loadMoreError, }) } diff --git a/src/state/models/feeds/post.ts b/src/state/models/feeds/post.ts index be341710..d064edc2 100644 --- a/src/state/models/feeds/post.ts +++ b/src/state/models/feeds/post.ts @@ -10,6 +10,7 @@ import {RootStoreModel} from '../root-store' import {updateDataOptimistically} from 'lib/async/revertible' import {track} from 'lib/analytics/analytics' import {hackAddDeletedEmbed} from 'lib/api/hack-add-deleted-embed' +import {logger} from '#/logger' type FeedViewPost = AppBskyFeedDefs.FeedViewPost type ReasonRepost = AppBskyFeedDefs.ReasonRepost @@ -42,14 +43,14 @@ export class PostsFeedItemModel { } else { this.postRecord = undefined this.richText = undefined - rootStore.log.warn('Received an invalid app.bsky.feed.post record', { + logger.warn('Received an invalid app.bsky.feed.post record', { error: valid.error, }) } } else { this.postRecord = undefined this.richText = undefined - rootStore.log.warn( + logger.warn( 'app.bsky.feed.getTimeline or app.bsky.feed.getAuthorFeed served an unexpected record type', {record: this.post.record}, ) @@ -132,7 +133,7 @@ export class PostsFeedItemModel { track('Post:Like') } } catch (error) { - this.rootStore.log.error('Failed to toggle like', {error}) + logger.error('Failed to toggle like', {error}) } } @@ -167,7 +168,7 @@ export class PostsFeedItemModel { track('Post:Repost') } } catch (error) { - this.rootStore.log.error('Failed to toggle repost', {error}) + logger.error('Failed to toggle repost', {error}) } } @@ -181,7 +182,7 @@ export class PostsFeedItemModel { track('Post:ThreadMute') } } catch (error) { - this.rootStore.log.error('Failed to toggle thread mute', {error}) + logger.error('Failed to toggle thread mute', {error}) } } @@ -190,7 +191,7 @@ export class PostsFeedItemModel { await this.rootStore.agent.deletePost(this.post.uri) this.rootStore.emitPostDeleted(this.post.uri) } catch (error) { - this.rootStore.log.error('Failed to delete post', {error}) + logger.error('Failed to delete post', {error}) } finally { track('Post:Delete') } diff --git a/src/state/models/feeds/posts.ts b/src/state/models/feeds/posts.ts index 5c10ae4c..0a06c581 100644 --- a/src/state/models/feeds/posts.ts +++ b/src/state/models/feeds/posts.ts @@ -22,6 +22,7 @@ import {LikesFeedAPI} from 'lib/api/feed/likes' import {CustomFeedAPI} from 'lib/api/feed/custom' import {ListFeedAPI} from 'lib/api/feed/list' import {MergeFeedAPI} from 'lib/api/feed/merge' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -161,7 +162,7 @@ export class PostsFeedModel { * Nuke all data */ clear() { - this.rootStore.log.debug('FeedModel:clear') + logger.debug('FeedModel:clear') this.isLoading = false this.isRefreshing = false this.hasNewLatest = false @@ -177,7 +178,7 @@ export class PostsFeedModel { * Load for first render */ setup = bundleAsync(async (isRefreshing: boolean = false) => { - this.rootStore.log.debug('FeedModel:setup', {isRefreshing}) + logger.debug('FeedModel:setup', {isRefreshing}) if (isRefreshing) { this.isRefreshing = true // set optimistically for UI } @@ -324,10 +325,10 @@ export class PostsFeedModel { this.knownError = detectKnownError(this.feedType, error) this.loadMoreError = cleanError(loadMoreError) if (error) { - this.rootStore.log.error('Posts feed request failed', {error}) + logger.error('Posts feed request failed', {error}) } if (loadMoreError) { - this.rootStore.log.error('Posts feed load-more request failed', { + logger.error('Posts feed load-more request failed', { error: loadMoreError, }) } diff --git a/src/state/models/invited-users.ts b/src/state/models/invited-users.ts index 995c4bfb..9ba65e19 100644 --- a/src/state/models/invited-users.ts +++ b/src/state/models/invited-users.ts @@ -2,6 +2,7 @@ import {makeAutoObservable, runInAction} from 'mobx' import {ComAtprotoServerDefs, AppBskyActorDefs} from '@atproto/api' import {RootStoreModel} from './root-store' import {isObj, hasProp, isStrArray} from 'lib/type-guards' +import {logger} from '#/logger' export class InvitedUsers { copiedInvites: string[] = [] @@ -63,7 +64,7 @@ export class InvitedUsers { }) this.rootStore.me.follows.hydrateMany(this.profiles) } catch (e) { - this.rootStore.log.error('Failed to fetch profiles for invited users', { + logger.error('Failed to fetch profiles for invited users', { error: e, }) } diff --git a/src/state/models/lists/actor-feeds.ts b/src/state/models/lists/actor-feeds.ts index 65da765f..29c01e53 100644 --- a/src/state/models/lists/actor-feeds.ts +++ b/src/state/models/lists/actor-feeds.ts @@ -4,6 +4,7 @@ import {RootStoreModel} from '../root-store' import {bundleAsync} from 'lib/async/bundle' import {cleanError} from 'lib/strings/errors' import {FeedSourceModel} from '../content/feed-source' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -98,7 +99,7 @@ export class ActorFeedsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user followers', {error: err}) + logger.error('Failed to fetch user followers', {error: err}) } } diff --git a/src/state/models/lists/blocked-accounts.ts b/src/state/models/lists/blocked-accounts.ts index b4495b54..5c3dbe7c 100644 --- a/src/state/models/lists/blocked-accounts.ts +++ b/src/state/models/lists/blocked-accounts.ts @@ -6,6 +6,7 @@ import { import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -86,7 +87,7 @@ export class BlockedAccountsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user followers', {error: err}) + logger.error('Failed to fetch user followers', {error: err}) } } diff --git a/src/state/models/lists/likes.ts b/src/state/models/lists/likes.ts index 61e480e1..df20f09d 100644 --- a/src/state/models/lists/likes.ts +++ b/src/state/models/lists/likes.ts @@ -5,6 +5,7 @@ import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' import * as apilib from 'lib/api/index' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -97,7 +98,7 @@ export class LikesModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch likes', {error: err}) + logger.error('Failed to fetch likes', {error: err}) } } diff --git a/src/state/models/lists/lists-list.ts b/src/state/models/lists/lists-list.ts index 7415d06d..eb629163 100644 --- a/src/state/models/lists/lists-list.ts +++ b/src/state/models/lists/lists-list.ts @@ -4,6 +4,7 @@ import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' import {accumulate} from 'lib/async/accumulate' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -204,10 +205,10 @@ export class ListsListModel { this.error = cleanError(err) this.loadMoreError = cleanError(loadMoreErr) if (err) { - this.rootStore.log.error('Failed to fetch user lists', {error: err}) + logger.error('Failed to fetch user lists', {error: err}) } if (loadMoreErr) { - this.rootStore.log.error('Failed to fetch user lists', { + logger.error('Failed to fetch user lists', { error: loadMoreErr, }) } diff --git a/src/state/models/lists/muted-accounts.ts b/src/state/models/lists/muted-accounts.ts index bc9e53e5..19ade0d9 100644 --- a/src/state/models/lists/muted-accounts.ts +++ b/src/state/models/lists/muted-accounts.ts @@ -6,6 +6,7 @@ import { import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -86,7 +87,7 @@ export class MutedAccountsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user followers', {error: err}) + logger.error('Failed to fetch user followers', {error: err}) } } diff --git a/src/state/models/lists/reposted-by.ts b/src/state/models/lists/reposted-by.ts index fe639fd0..c5058558 100644 --- a/src/state/models/lists/reposted-by.ts +++ b/src/state/models/lists/reposted-by.ts @@ -8,6 +8,7 @@ import {RootStoreModel} from '../root-store' import {bundleAsync} from 'lib/async/bundle' import {cleanError} from 'lib/strings/errors' import * as apilib from 'lib/api/index' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -100,7 +101,7 @@ export class RepostedByModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch reposted by view', {error: err}) + logger.error('Failed to fetch reposted by view', {error: err}) } } diff --git a/src/state/models/lists/user-followers.ts b/src/state/models/lists/user-followers.ts index d76ecce1..159308b9 100644 --- a/src/state/models/lists/user-followers.ts +++ b/src/state/models/lists/user-followers.ts @@ -6,6 +6,7 @@ import { import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -99,7 +100,7 @@ export class UserFollowersModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user followers', {error: err}) + logger.error('Failed to fetch user followers', {error: err}) } } diff --git a/src/state/models/lists/user-follows.ts b/src/state/models/lists/user-follows.ts index c9630eba..3abbbaf9 100644 --- a/src/state/models/lists/user-follows.ts +++ b/src/state/models/lists/user-follows.ts @@ -6,6 +6,7 @@ import { import {RootStoreModel} from '../root-store' import {cleanError} from 'lib/strings/errors' import {bundleAsync} from 'lib/async/bundle' +import {logger} from '#/logger' const PAGE_SIZE = 30 @@ -99,7 +100,7 @@ export class UserFollowsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user follows', err) + logger.error('Failed to fetch user follows', err) } } diff --git a/src/state/models/log.ts b/src/state/models/log.ts deleted file mode 100644 index 7c9c37c0..00000000 --- a/src/state/models/log.ts +++ /dev/null @@ -1,115 +0,0 @@ -import {makeAutoObservable} from 'mobx' -// import {XRPCError, XRPCInvalidResponseError} from '@atproto/xrpc' TODO - -const MAX_ENTRIES = 300 - -interface LogEntry { - id: string - type?: string - summary?: string - details?: string - ts?: number -} - -let _lastTs: string -let _lastId: string -function genId(): string { - let candidate = String(Date.now()) - if (_lastTs === candidate) { - const id = _lastId + 'x' - _lastId = id - return id - } - _lastTs = candidate - _lastId = candidate - return candidate -} - -export class LogModel { - entries: LogEntry[] = [] - timers = new Map() - - constructor() { - makeAutoObservable(this) - } - - add(entry: LogEntry) { - this.entries.push(entry) - while (this.entries.length > MAX_ENTRIES) { - this.entries = this.entries.slice(50) - } - } - - debug(summary: string, details?: any) { - details = detailsToStr(details) - console.debug(summary, details || '') - this.add({ - id: genId(), - type: 'debug', - summary, - details, - ts: Date.now(), - }) - } - - warn(summary: string, details?: any) { - details = detailsToStr(details) - console.debug(summary, details || '') - this.add({ - id: genId(), - type: 'warn', - summary, - details, - ts: Date.now(), - }) - } - - error(summary: string, details?: any) { - details = detailsToStr(details) - console.debug(summary, details || '') - this.add({ - id: genId(), - type: 'error', - summary, - details, - ts: Date.now(), - }) - } - - time = (label = 'default') => { - this.timers.set(label, performance.now()) - } - - timeEnd = (label = 'default', warn = false) => { - const endTime = performance.now() - if (this.timers.has(label)) { - const elapsedTime = endTime - this.timers.get(label)! - console.log(`${label}: ${elapsedTime.toFixed(3)}ms`) - this.timers.delete(label) - } else { - warn && console.warn(`Timer with label '${label}' does not exist.`) - } - } -} - -function detailsToStr(details?: any) { - if (details && typeof details !== 'string') { - if ( - // details instanceof XRPCInvalidResponseError || TODO - details.constructor.name === 'XRPCInvalidResponseError' - ) { - return `The server gave an ill-formatted response.\nMethod: ${ - details.lexiconNsid - }.\nError: ${details.validationError.toString()}` - } else if ( - // details instanceof XRPCError || TODO - details.constructor.name === 'XRPCError' - ) { - return `An XRPC error occurred.\nStatus: ${details.status}\nError: ${details.error}\nMessage: ${details.message}` - } else if (details instanceof Error) { - return details.toString() - } - return JSON.stringify(details, null, 2) - } - return details -} diff --git a/src/state/models/me.ts b/src/state/models/me.ts index 14b2ef84..d12cb68c 100644 --- a/src/state/models/me.ts +++ b/src/state/models/me.ts @@ -9,6 +9,7 @@ import {NotificationsFeedModel} from './feeds/notifications' import {MyFeedsUIModel} from './ui/my-feeds' import {MyFollowsCache} from './cache/my-follows' import {isObj, hasProp} from 'lib/type-guards' +import {logger} from '#/logger' const PROFILE_UPDATE_INTERVAL = 10 * 60 * 1e3 // 10min const NOTIFS_UPDATE_INTERVAL = 30 * 1e3 // 30sec @@ -104,21 +105,21 @@ export class MeModel { async load() { const sess = this.rootStore.session - this.rootStore.log.debug('MeModel:load', {hasSession: sess.hasSession}) + logger.debug('MeModel:load', {hasSession: sess.hasSession}) if (sess.hasSession) { this.did = sess.currentSession?.did || '' await this.fetchProfile() this.mainFeed.clear() /* dont await */ this.mainFeed.setup().catch(e => { - this.rootStore.log.error('Failed to setup main feed model', {error: e}) + logger.error('Failed to setup main feed model', {error: e}) }) /* dont await */ this.notifications.setup().catch(e => { - this.rootStore.log.error('Failed to setup notifications model', { + logger.error('Failed to setup notifications model', { error: e, }) }) /* dont await */ this.notifications.setup().catch(e => { - this.rootStore.log.error('Failed to setup notifications model', { + logger.error('Failed to setup notifications model', { error: e, }) }) @@ -134,7 +135,7 @@ export class MeModel { async updateIfNeeded() { if (Date.now() - this.lastProfileStateUpdate > PROFILE_UPDATE_INTERVAL) { - this.rootStore.log.debug('Updating me profile information') + logger.debug('Updating me profile information') this.lastProfileStateUpdate = Date.now() await this.fetchProfile() await this.fetchInviteCodes() @@ -188,7 +189,7 @@ export class MeModel { }) }) } catch (e) { - this.rootStore.log.error('Failed to fetch user invite codes', { + logger.error('Failed to fetch user invite codes', { error: e, }) } @@ -205,7 +206,7 @@ export class MeModel { this.appPasswords = res.data.passwords }) } catch (e) { - this.rootStore.log.error('Failed to fetch user app passwords', { + logger.error('Failed to fetch user app passwords', { error: e, }) } @@ -228,7 +229,7 @@ export class MeModel { }) return res.data } catch (e) { - this.rootStore.log.error('Failed to create app password', {error: e}) + logger.error('Failed to create app password', {error: e}) } } } @@ -243,7 +244,7 @@ export class MeModel { this.appPasswords = this.appPasswords.filter(p => p.name !== name) }) } catch (e) { - this.rootStore.log.error('Failed to delete app password', {error: e}) + logger.error('Failed to delete app password', {error: e}) } } } diff --git a/src/state/models/media/image.ts b/src/state/models/media/image.ts index 4ca0b47c..b3796060 100644 --- a/src/state/models/media/image.ts +++ b/src/state/models/media/image.ts @@ -9,6 +9,7 @@ import {ActionCrop, FlipType, SaveFormat} from 'expo-image-manipulator' import {Position} from 'react-avatar-editor' import {Dimensions} from 'lib/media/types' import {isIOS} from 'platform/detection' +import {logger} from '#/logger' export interface ImageManipulationAttributes { aspectRatio?: '4:3' | '1:1' | '3:4' | 'None' @@ -188,7 +189,7 @@ export class ImageModel implements Omit { this.cropped = cropped }) } catch (err) { - this.rootStore.log.error('Failed to crop photo', {error: err}) + logger.error('Failed to crop photo', {error: err}) } } diff --git a/src/state/models/root-store.ts b/src/state/models/root-store.ts index 621c87c1..cf7307ca 100644 --- a/src/state/models/root-store.ts +++ b/src/state/models/root-store.ts @@ -41,7 +41,6 @@ export type AppInfo = z.infer export class RootStoreModel { agent: BskyAgent appInfo?: AppInfo - log = logger session = new SessionModel(this) shell = new ShellUiModel(this) preferences = new PreferencesModel(this) @@ -122,15 +121,15 @@ export class RootStoreModel { * Called during init to resume any stored session. */ async attemptSessionResumption() { - this.log.debug('RootStoreModel:attemptSessionResumption') + logger.debug('RootStoreModel:attemptSessionResumption') try { await this.session.attemptSessionResumption() - this.log.debug('Session initialized', { + logger.debug('Session initialized', { hasSession: this.session.hasSession, }) this.updateSessionState() } catch (e: any) { - this.log.warn('Failed to initialize session', {error: e}) + logger.warn('Failed to initialize session', {error: e}) } } @@ -141,7 +140,7 @@ export class RootStoreModel { agent: BskyAgent, {hadSession}: {hadSession: boolean}, ) { - this.log.debug('RootStoreModel:handleSessionChange') + logger.debug('RootStoreModel:handleSessionChange') this.agent = agent applyDebugHeader(this.agent) this.me.clear() @@ -157,7 +156,7 @@ export class RootStoreModel { * Called by the session model. Handles session drops by informing the user. */ async handleSessionDrop() { - this.log.debug('RootStoreModel:handleSessionDrop') + logger.debug('RootStoreModel:handleSessionDrop') resetToTab('HomeTab') this.me.clear() this.emitSessionDropped() @@ -167,7 +166,7 @@ export class RootStoreModel { * Clears all session-oriented state. */ clearAllSessionState() { - this.log.debug('RootStoreModel:clearAllSessionState') + logger.debug('RootStoreModel:clearAllSessionState') this.session.clear() resetToTab('HomeTab') this.me.clear() @@ -184,7 +183,7 @@ export class RootStoreModel { await this.me.updateIfNeeded() await this.preferences.sync() } catch (e: any) { - this.log.error('Failed to fetch latest state', {error: e}) + logger.error('Failed to fetch latest state', {error: e}) } } diff --git a/src/state/models/session.ts b/src/state/models/session.ts index 7cd3c122..5b95c7d3 100644 --- a/src/state/models/session.ts +++ b/src/state/models/session.ts @@ -12,6 +12,7 @@ import {z} from 'zod' import {RootStoreModel} from './root-store' import {IS_PROD} from 'lib/constants' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' export type ServiceDescription = DescribeServer.OutputSchema @@ -56,7 +57,7 @@ export class SessionModel { ), isResumingSession: this.isResumingSession, } - this.rootStore.log.debug(message, details) + logger.debug(message, details, logger.DebugContext.session) } /** diff --git a/src/state/models/ui/create-account.ts b/src/state/models/ui/create-account.ts index 3bd39ba7..1711b530 100644 --- a/src/state/models/ui/create-account.ts +++ b/src/state/models/ui/create-account.ts @@ -8,6 +8,7 @@ import {createFullHandle} from 'lib/strings/handles' import {cleanError} from 'lib/strings/errors' import {getAge} from 'lib/strings/time' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' const DEFAULT_DATE = new Date(Date.now() - 60e3 * 60 * 24 * 365 * 20) // default to 20 years ago @@ -76,7 +77,7 @@ export class CreateAccountModel { this.setServiceDescription(desc) this.setUserDomain(desc.availableUserDomains[0]) } catch (err: any) { - this.rootStore.log.warn( + logger.warn( `Failed to fetch service description for ${this.serviceUrl}`, {error: err}, ) @@ -127,7 +128,7 @@ export class CreateAccountModel { errMsg = 'Invite code not accepted. Check that you input it correctly and try again.' } - this.rootStore.log.error('Failed to create account', {error: e}) + logger.error('Failed to create account', {error: e}) this.setIsProcessing(false) this.setError(cleanError(errMsg)) throw e diff --git a/src/state/models/ui/preferences.ts b/src/state/models/ui/preferences.ts index 7714d65d..6e43198a 100644 --- a/src/state/models/ui/preferences.ts +++ b/src/state/models/ui/preferences.ts @@ -14,6 +14,7 @@ import {deviceLocales} from 'platform/detection' import {getAge} from 'lib/strings/time' import {FeedTuner} from 'lib/api/feed-manip' import {LANGUAGES} from '../../../locale/languages' +import {logger} from '#/logger' // TEMP we need to permanently convert 'show' to 'ignore', for now we manually convert -prf export type LabelPreference = APILabelPreference | 'show' @@ -246,7 +247,7 @@ export class PreferencesModel { }) await this.rootStore.agent.setSavedFeeds(saved, pinned) } catch (error) { - this.rootStore.log.error('Failed to set default feeds', {error}) + logger.error('Failed to set default feeds', {error}) } } } finally { diff --git a/src/state/models/ui/profile.ts b/src/state/models/ui/profile.ts index 47a99a8f..f96340c6 100644 --- a/src/state/models/ui/profile.ts +++ b/src/state/models/ui/profile.ts @@ -4,6 +4,7 @@ import {ProfileModel} from '../content/profile' import {PostsFeedModel} from '../feeds/posts' import {ActorFeedsModel} from '../lists/actor-feeds' import {ListsListModel} from '../lists/lists-list' +import {logger} from '#/logger' export enum Sections { PostsNoReplies = 'Posts', @@ -223,14 +224,10 @@ export class ProfileUiModel { await Promise.all([ this.profile .setup() - .catch(err => - this.rootStore.log.error('Failed to fetch profile', {error: err}), - ), + .catch(err => logger.error('Failed to fetch profile', {error: err})), this.feed .setup() - .catch(err => - this.rootStore.log.error('Failed to fetch feed', {error: err}), - ), + .catch(err => logger.error('Failed to fetch feed', {error: err})), ]) runInAction(() => { this.isAuthenticatedUser = @@ -241,9 +238,7 @@ export class ProfileUiModel { this.lists.source = this.profile.did this.lists .loadMore() - .catch(err => - this.rootStore.log.error('Failed to fetch lists', {error: err}), - ) + .catch(err => logger.error('Failed to fetch lists', {error: err})) } async refresh() { diff --git a/src/state/models/ui/saved-feeds.ts b/src/state/models/ui/saved-feeds.ts index 72055abe..fd84edc0 100644 --- a/src/state/models/ui/saved-feeds.ts +++ b/src/state/models/ui/saved-feeds.ts @@ -4,6 +4,7 @@ import {bundleAsync} from 'lib/async/bundle' import {cleanError} from 'lib/strings/errors' import {FeedSourceModel} from '../content/feed-source' import {track} from 'lib/analytics/analytics' +import {logger} from '#/logger' export class SavedFeedsModel { // state @@ -126,7 +127,7 @@ export class SavedFeedsModel { this.hasLoaded = true this.error = cleanError(err) if (err) { - this.rootStore.log.error('Failed to fetch user feeds', {err}) + logger.error('Failed to fetch user feeds', {err}) } } diff --git a/src/view/com/auth/login/Login.tsx b/src/view/com/auth/login/Login.tsx index 348580fa..acc05b6c 100644 --- a/src/view/com/auth/login/Login.tsx +++ b/src/view/com/auth/login/Login.tsx @@ -30,6 +30,7 @@ import {usePalette} from 'lib/hooks/usePalette' import {useTheme} from 'lib/ThemeContext' import {cleanError} from 'lib/strings/errors' import {isWeb} from 'platform/detection' +import {logger} from '#/logger' enum Forms { Login, @@ -81,10 +82,9 @@ export const Login = ({onPressBack}: {onPressBack: () => void}) => { if (aborted) { return } - store.log.warn( - `Failed to fetch service description for ${serviceUrl}`, - {error: err}, - ) + logger.warn(`Failed to fetch service description for ${serviceUrl}`, { + error: err, + }) setError( 'Unable to contact your service. Please check your Internet connection.', ) @@ -93,7 +93,7 @@ export const Login = ({onPressBack}: {onPressBack: () => void}) => { return () => { aborted = true } - }, [store.session, store.log, serviceUrl, retryDescribeTrigger]) + }, [store.session, serviceUrl, retryDescribeTrigger]) const onPressRetryConnect = () => setRetryDescribeTrigger({}) const onPressForgotPassword = () => { @@ -349,7 +349,7 @@ const LoginForm = ({ }) } catch (e: any) { const errMsg = e.toString() - store.log.warn('Failed to login', {error: e}) + logger.warn('Failed to login', {error: e}) setIsProcessing(false) if (errMsg.includes('Authentication Required')) { setError('Invalid username or password') @@ -578,7 +578,7 @@ const ForgotPasswordForm = ({ onEmailSent() } catch (e: any) { const errMsg = e.toString() - store.log.warn('Failed to request password reset', {error: e}) + logger.warn('Failed to request password reset', {error: e}) setIsProcessing(false) if (isNetworkError(e)) { setError( @@ -694,7 +694,6 @@ const ForgotPasswordForm = ({ } const SetNewPasswordForm = ({ - store, error, serviceUrl, setError, @@ -734,7 +733,7 @@ const SetNewPasswordForm = ({ onPasswordSet() } catch (e: any) { const errMsg = e.toString() - store.log.warn('Failed to set new password', {error: e}) + logger.warn('Failed to set new password', {error: e}) setIsProcessing(false) if (isNetworkError(e)) { setError( diff --git a/src/view/com/composer/photos/OpenCameraBtn.tsx b/src/view/com/composer/photos/OpenCameraBtn.tsx index bd4d4b65..99e820d5 100644 --- a/src/view/com/composer/photos/OpenCameraBtn.tsx +++ b/src/view/com/composer/photos/OpenCameraBtn.tsx @@ -12,6 +12,7 @@ import {useCameraPermission} from 'lib/hooks/usePermissions' import {HITSLOP_10, POST_IMG_MAX} from 'lib/constants' import {GalleryModel} from 'state/models/media/gallery' import {isMobileWeb, isNative} from 'platform/detection' +import {logger} from '#/logger' type Props = { gallery: GalleryModel @@ -39,7 +40,7 @@ export function OpenCameraBtn({gallery}: Props) { gallery.add(img) } catch (err: any) { // ignore - store.log.warn('Error using camera', {error: err}) + logger.warn('Error using camera', {error: err}) } }, [gallery, track, store, requestCameraAccessIfNeeded]) diff --git a/src/view/com/composer/useExternalLinkFetch.ts b/src/view/com/composer/useExternalLinkFetch.ts index aa5b4b43..eda1a670 100644 --- a/src/view/com/composer/useExternalLinkFetch.ts +++ b/src/view/com/composer/useExternalLinkFetch.ts @@ -16,6 +16,7 @@ import { } from 'lib/strings/url-helpers' import {ComposerOpts} from 'state/models/ui/shell' import {POST_IMG_MAX} from 'lib/constants' +import {logger} from '#/logger' export function useExternalLinkFetch({ setQuote, @@ -46,7 +47,7 @@ export function useExternalLinkFetch({ setExtLink(undefined) }, err => { - store.log.error('Failed to fetch post for quote embedding', { + logger.error('Failed to fetch post for quote embedding', { error: err, }) setExtLink(undefined) @@ -66,7 +67,7 @@ export function useExternalLinkFetch({ }) }, err => { - store.log.error('Failed to fetch feed for embedding', {error: err}) + logger.error('Failed to fetch feed for embedding', {error: err}) setExtLink(undefined) }, ) @@ -84,7 +85,7 @@ export function useExternalLinkFetch({ }) }, err => { - store.log.error('Failed to fetch list for embedding', {error: err}) + logger.error('Failed to fetch list for embedding', {error: err}) setExtLink(undefined) }, ) diff --git a/src/view/com/feeds/FeedPage.tsx b/src/view/com/feeds/FeedPage.tsx index 72b83b80..b4d25781 100644 --- a/src/view/com/feeds/FeedPage.tsx +++ b/src/view/com/feeds/FeedPage.tsx @@ -20,6 +20,7 @@ import {TextLink} from '../util/Link' import {FAB} from '../util/fab/FAB' import {LoadLatestBtn} from '../util/load-latest/LoadLatestBtn' import useAppState from 'react-native-appstate-hook' +import {logger} from '#/logger' export const FeedPage = observer(function FeedPageImpl({ testID, @@ -66,10 +67,10 @@ export const FeedPage = observer(function FeedPageImpl({ if (feed.isLoading) { return } - store.log.debug('HomeScreen: Polling for new posts') + logger.debug('HomeScreen: Polling for new posts') feed.checkForLatest() }, - [appState, isScreenFocused, isPageFocused, store, feed], + [appState, isScreenFocused, isPageFocused, feed], ) const scrollToTop = React.useCallback(() => { @@ -96,7 +97,7 @@ export const FeedPage = observer(function FeedPageImpl({ const pollInterval = setInterval(doPoll, POLL_FREQ) screen('Feed') - store.log.debug('HomeScreen: Updating feed') + logger.debug('HomeScreen: Updating feed') feed.checkForLatest() return () => { diff --git a/src/view/com/feeds/FeedSourceCard.tsx b/src/view/com/feeds/FeedSourceCard.tsx index 060a4b63..2c4335dc 100644 --- a/src/view/com/feeds/FeedSourceCard.tsx +++ b/src/view/com/feeds/FeedSourceCard.tsx @@ -15,6 +15,7 @@ import {pluralize} from 'lib/strings/helpers' import {AtUri} from '@atproto/api' import * as Toast from 'view/com/util/Toast' import {sanitizeHandle} from 'lib/strings/handles' +import {logger} from '#/logger' export const FeedSourceCard = observer(function FeedSourceCardImpl({ item, @@ -45,7 +46,7 @@ export const FeedSourceCard = observer(function FeedSourceCardImpl({ Toast.show('Removed from my feeds') } catch (e) { Toast.show('There was an issue contacting your server') - store.log.error('Failed to unsave feed', {error: e}) + logger.error('Failed to unsave feed', {error: e}) } }, }) @@ -55,7 +56,7 @@ export const FeedSourceCard = observer(function FeedSourceCardImpl({ Toast.show('Added to my feeds') } catch (e) { Toast.show('There was an issue contacting your server') - store.log.error('Failed to save feed', {error: e}) + logger.error('Failed to save feed', {error: e}) } } }, [store, item]) diff --git a/src/view/com/lists/ListItems.tsx b/src/view/com/lists/ListItems.tsx index 76cd5e7c..192cdd9d 100644 --- a/src/view/com/lists/ListItems.tsx +++ b/src/view/com/lists/ListItems.tsx @@ -21,6 +21,7 @@ import {useStores} from 'state/index' import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import {s} from 'lib/styles' import {OnScrollCb} from 'lib/hooks/useOnMainScroll' +import {logger} from '#/logger' const LOADING_ITEM = {_reactKey: '__loading__'} const EMPTY_ITEM = {_reactKey: '__empty__'} @@ -94,7 +95,7 @@ export const ListItems = observer(function ListItemsImpl({ try { await list.refresh() } catch (err) { - list.rootStore.log.error('Failed to refresh lists', {error: err}) + logger.error('Failed to refresh lists', {error: err}) } setIsRefreshing(false) }, [list, track, setIsRefreshing]) @@ -104,7 +105,7 @@ export const ListItems = observer(function ListItemsImpl({ try { await list.loadMore() } catch (err) { - list.rootStore.log.error('Failed to load more lists', {error: err}) + logger.error('Failed to load more lists', {error: err}) } }, [list, track]) diff --git a/src/view/com/lists/ListsList.tsx b/src/view/com/lists/ListsList.tsx index c0acaa96..e42b6575 100644 --- a/src/view/com/lists/ListsList.tsx +++ b/src/view/com/lists/ListsList.tsx @@ -19,6 +19,7 @@ import {useAnalytics} from 'lib/analytics/analytics' import {usePalette} from 'lib/hooks/usePalette' import {FlatList} from '../util/Views.web' import {s} from 'lib/styles' +import {logger} from '#/logger' const LOADING = {_reactKey: '__loading__'} const EMPTY = {_reactKey: '__empty__'} @@ -78,7 +79,7 @@ export const ListsList = observer(function ListsListImpl({ try { await listsList.refresh() } catch (err) { - listsList.rootStore.log.error('Failed to refresh lists', {error: err}) + logger.error('Failed to refresh lists', {error: err}) } setIsRefreshing(false) }, [listsList, track, setIsRefreshing]) @@ -88,7 +89,7 @@ export const ListsList = observer(function ListsListImpl({ try { await listsList.loadMore() } catch (err) { - listsList.rootStore.log.error('Failed to load more lists', {error: err}) + logger.error('Failed to load more lists', {error: err}) } }, [listsList, track]) diff --git a/src/view/com/modals/AddAppPasswords.tsx b/src/view/com/modals/AddAppPasswords.tsx index 71199e34..29763620 100644 --- a/src/view/com/modals/AddAppPasswords.tsx +++ b/src/view/com/modals/AddAppPasswords.tsx @@ -12,6 +12,7 @@ import { } from '@fortawesome/react-native-fontawesome' import Clipboard from '@react-native-clipboard/clipboard' import * as Toast from '../util/Toast' +import {logger} from '#/logger' export const snapPoints = ['70%'] @@ -95,7 +96,7 @@ export function Component({}: {}) { } } catch (e) { Toast.show('Failed to create app password.') - store.log.error('Failed to create app password', {error: e}) + logger.error('Failed to create app password', {error: e}) } } diff --git a/src/view/com/modals/ChangeHandle.tsx b/src/view/com/modals/ChangeHandle.tsx index 2fb1a503..d197083a 100644 --- a/src/view/com/modals/ChangeHandle.tsx +++ b/src/view/com/modals/ChangeHandle.tsx @@ -21,6 +21,7 @@ import {usePalette} from 'lib/hooks/usePalette' import {useTheme} from 'lib/ThemeContext' import {useAnalytics} from 'lib/analytics/analytics' import {cleanError} from 'lib/strings/errors' +import {logger} from '#/logger' export const snapPoints = ['100%'] @@ -65,7 +66,7 @@ export function Component({onChanged}: {onChanged: () => void}) { return } setProcessing(false) - store.log.warn( + logger.warn( `Failed to fetch service description for ${String( store.agent.service, )}`, @@ -79,7 +80,7 @@ export function Component({onChanged}: {onChanged: () => void}) { return () => { aborted = true } - }, [store.agent.service, store.session, store.log, retryDescribeTrigger]) + }, [store.agent.service, store.session, retryDescribeTrigger]) // events // = @@ -105,7 +106,7 @@ export function Component({onChanged}: {onChanged: () => void}) { try { track('EditHandle:SetNewHandle') const newHandle = isCustom ? handle : createFullHandle(handle, userDomain) - store.log.debug(`Updating handle to ${newHandle}`) + logger.debug(`Updating handle to ${newHandle}`) await store.agent.updateHandle({ handle: newHandle, }) @@ -113,7 +114,7 @@ export function Component({onChanged}: {onChanged: () => void}) { onChanged() } catch (err: any) { setError(cleanError(err)) - store.log.error('Failed to update handle', {handle, error: err}) + logger.error('Failed to update handle', {handle, error: err}) } finally { setProcessing(false) } @@ -343,7 +344,7 @@ function CustomHandleForm({ } } catch (err: any) { setError(cleanError(err)) - store.log.error('Failed to verify domain', {handle, error: err}) + logger.error('Failed to verify domain', {handle, error: err}) } finally { setIsVerifying(false) } @@ -355,7 +356,6 @@ function CustomHandleForm({ setError, canSave, onPressSave, - store.log, store.agent, ]) diff --git a/src/view/com/modals/ContentFilteringSettings.tsx b/src/view/com/modals/ContentFilteringSettings.tsx index b78846bd..9075d027 100644 --- a/src/view/com/modals/ContentFilteringSettings.tsx +++ b/src/view/com/modals/ContentFilteringSettings.tsx @@ -15,6 +15,7 @@ import {CONFIGURABLE_LABEL_GROUPS} from 'lib/labeling/const' import {isIOS} from 'platform/detection' import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import * as Toast from '../util/Toast' +import {logger} from '#/logger' export const snapPoints = ['90%'] @@ -103,7 +104,7 @@ const AdultContentEnabledPref = observer( Toast.show( 'There was an issue syncing your preferences with the server', ) - store.log.error('Failed to update preferences with server', {error: e}) + logger.error('Failed to update preferences with server', {error: e}) } } @@ -168,7 +169,7 @@ const ContentLabelPref = observer(function ContentLabelPrefImpl({ Toast.show( 'There was an issue syncing your preferences with the server', ) - store.log.error('Failed to update preferences with server', {error: e}) + logger.error('Failed to update preferences with server', {error: e}) } }, [store, group], diff --git a/src/view/com/modals/UserAddRemoveLists.tsx b/src/view/com/modals/UserAddRemoveLists.tsx index 32da6403..aeec2e87 100644 --- a/src/view/com/modals/UserAddRemoveLists.tsx +++ b/src/view/com/modals/UserAddRemoveLists.tsx @@ -20,6 +20,7 @@ import {s} from 'lib/styles' import {usePalette} from 'lib/hooks/usePalette' import {isWeb, isAndroid} from 'platform/detection' import isEqual from 'lodash.isequal' +import {logger} from '#/logger' export const snapPoints = ['fullscreen'] @@ -62,7 +63,7 @@ export const Component = observer(function UserAddRemoveListsImpl({ setMembershipsLoaded(true) }, err => { - store.log.error('Failed to fetch memberships', {error: err}) + logger.error('Failed to fetch memberships', {error: err}) }, ) }, [memberships, listsList, store, setSelected, setMembershipsLoaded]) @@ -76,7 +77,7 @@ export const Component = observer(function UserAddRemoveListsImpl({ try { changes = await memberships.updateTo(selected) } catch (err) { - store.log.error('Failed to update memberships', {error: err}) + logger.error('Failed to update memberships', {error: err}) return } Toast.show('Lists updated') diff --git a/src/view/com/notifications/Feed.tsx b/src/view/com/notifications/Feed.tsx index ef16f598..74769bc7 100644 --- a/src/view/com/notifications/Feed.tsx +++ b/src/view/com/notifications/Feed.tsx @@ -11,6 +11,7 @@ import {EmptyState} from '../util/EmptyState' import {OnScrollCb} from 'lib/hooks/useOnMainScroll' import {s} from 'lib/styles' import {usePalette} from 'lib/hooks/usePalette' +import {logger} from '#/logger' const EMPTY_FEED_ITEM = {_reactKey: '__empty__'} const LOAD_MORE_ERROR_ITEM = {_reactKey: '__load_more_error__'} @@ -61,7 +62,7 @@ export const Feed = observer(function Feed({ setIsPTRing(true) await view.refresh() } catch (err) { - view.rootStore.log.error('Failed to refresh notifications feed', { + logger.error('Failed to refresh notifications feed', { error: err, }) } finally { @@ -73,7 +74,7 @@ export const Feed = observer(function Feed({ try { await view.loadMore() } catch (err) { - view.rootStore.log.error('Failed to load more notifications', { + logger.error('Failed to load more notifications', { error: err, }) } diff --git a/src/view/com/post-thread/PostLikedBy.tsx b/src/view/com/post-thread/PostLikedBy.tsx index d16e8d30..22ff035d 100644 --- a/src/view/com/post-thread/PostLikedBy.tsx +++ b/src/view/com/post-thread/PostLikedBy.tsx @@ -7,6 +7,7 @@ import {ErrorMessage} from '../util/error/ErrorMessage' import {ProfileCardWithFollowBtn} from '../profile/ProfileCard' import {useStores} from 'state/index' import {usePalette} from 'lib/hooks/usePalette' +import {logger} from '#/logger' export const PostLikedBy = observer(function PostLikedByImpl({ uri, @@ -20,8 +21,8 @@ export const PostLikedBy = observer(function PostLikedByImpl({ useEffect(() => { view .loadMore() - .catch(err => store.log.error('Failed to fetch likes', {error: err})) - }, [view, store.log]) + .catch(err => logger.error('Failed to fetch likes', {error: err})) + }, [view]) const onRefresh = () => { view.refresh() @@ -29,9 +30,7 @@ export const PostLikedBy = observer(function PostLikedByImpl({ const onEndReached = () => { view .loadMore() - .catch(err => - view?.rootStore.log.error('Failed to load more likes', {error: err}), - ) + .catch(err => logger.error('Failed to load more likes', {error: err})) } if (!view.hasLoaded) { diff --git a/src/view/com/post-thread/PostRepostedBy.tsx b/src/view/com/post-thread/PostRepostedBy.tsx index 0e681777..29a79530 100644 --- a/src/view/com/post-thread/PostRepostedBy.tsx +++ b/src/view/com/post-thread/PostRepostedBy.tsx @@ -7,6 +7,7 @@ import {ProfileCardWithFollowBtn} from '../profile/ProfileCard' import {ErrorMessage} from '../util/error/ErrorMessage' import {useStores} from 'state/index' import {usePalette} from 'lib/hooks/usePalette' +import {logger} from '#/logger' export const PostRepostedBy = observer(function PostRepostedByImpl({ uri, @@ -23,8 +24,8 @@ export const PostRepostedBy = observer(function PostRepostedByImpl({ useEffect(() => { view .loadMore() - .catch(err => store.log.error('Failed to fetch reposts', {error: err})) - }, [view, store.log]) + .catch(err => logger.error('Failed to fetch reposts', {error: err})) + }, [view]) const onRefresh = () => { view.refresh() @@ -32,9 +33,7 @@ export const PostRepostedBy = observer(function PostRepostedByImpl({ const onEndReached = () => { view .loadMore() - .catch(err => - view?.rootStore.log.error('Failed to load more reposts', {error: err}), - ) + .catch(err => logger.error('Failed to load more reposts', {error: err})) } if (!view.hasLoaded) { diff --git a/src/view/com/post-thread/PostThread.tsx b/src/view/com/post-thread/PostThread.tsx index b0728a8a..4eb47b0a 100644 --- a/src/view/com/post-thread/PostThread.tsx +++ b/src/view/com/post-thread/PostThread.tsx @@ -30,6 +30,7 @@ import {useNavigation} from '@react-navigation/native' import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import {NavigationProp} from 'lib/routes/types' import {sanitizeDisplayName} from 'lib/strings/display-names' +import {logger} from '#/logger' const MAINTAIN_VISIBLE_CONTENT_POSITION = {minIndexForVisible: 2} @@ -119,7 +120,7 @@ export const PostThread = observer(function PostThread({ try { view?.refresh() } catch (err) { - view.rootStore.log.error('Failed to refresh posts thread', {error: err}) + logger.error('Failed to refresh posts thread', {error: err}) } setIsRefreshing(false) }, [view, setIsRefreshing]) diff --git a/src/view/com/post-thread/PostThreadItem.tsx b/src/view/com/post-thread/PostThreadItem.tsx index 43026916..351a4670 100644 --- a/src/view/com/post-thread/PostThreadItem.tsx +++ b/src/view/com/post-thread/PostThreadItem.tsx @@ -36,6 +36,7 @@ import {TimeElapsed} from 'view/com/util/TimeElapsed' import {makeProfileLink} from 'lib/routes/links' import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import {MAX_POST_LINES} from 'lib/constants' +import {logger} from '#/logger' export const PostThreadItem = observer(function PostThreadItem({ item, @@ -111,14 +112,14 @@ export const PostThreadItem = observer(function PostThreadItem({ const onPressToggleRepost = React.useCallback(() => { return item .toggleRepost() - .catch(e => store.log.error('Failed to toggle repost', {error: e})) - }, [item, store]) + .catch(e => logger.error('Failed to toggle repost', {error: e})) + }, [item]) const onPressToggleLike = React.useCallback(() => { return item .toggleLike() - .catch(e => store.log.error('Failed to toggle like', {error: e})) - }, [item, store]) + .catch(e => logger.error('Failed to toggle like', {error: e})) + }, [item]) const onCopyPostText = React.useCallback(() => { Clipboard.setString(record?.text || '') @@ -138,9 +139,9 @@ export const PostThreadItem = observer(function PostThreadItem({ Toast.show('You will now receive notifications for this thread') } } catch (e) { - store.log.error('Failed to toggle thread mute', {error: e}) + logger.error('Failed to toggle thread mute', {error: e}) } - }, [item, store]) + }, [item]) const onDeletePost = React.useCallback(() => { item.delete().then( @@ -149,11 +150,11 @@ export const PostThreadItem = observer(function PostThreadItem({ Toast.show('Post deleted') }, e => { - store.log.error('Failed to delete post', {error: e}) + logger.error('Failed to delete post', {error: e}) Toast.show('Failed to delete post, please try again') }, ) - }, [item, store]) + }, [item]) const onPressShowMore = React.useCallback(() => { setLimitLines(false) diff --git a/src/view/com/post/Post.tsx b/src/view/com/post/Post.tsx index 8f862f32..4ec9db77 100644 --- a/src/view/com/post/Post.tsx +++ b/src/view/com/post/Post.tsx @@ -32,6 +32,7 @@ import {getTranslatorLink} from '../../../locale/helpers' import {makeProfileLink} from 'lib/routes/links' import {MAX_POST_LINES} from 'lib/constants' import {countLines} from 'lib/strings/helpers' +import {logger} from '#/logger' export const Post = observer(function PostImpl({ view, @@ -142,14 +143,14 @@ const PostLoaded = observer(function PostLoadedImpl({ const onPressToggleRepost = React.useCallback(() => { return item .toggleRepost() - .catch(e => store.log.error('Failed to toggle repost', {error: e})) - }, [item, store]) + .catch(e => logger.error('Failed to toggle repost', {error: e})) + }, [item]) const onPressToggleLike = React.useCallback(() => { return item .toggleLike() - .catch(e => store.log.error('Failed to toggle like', {error: e})) - }, [item, store]) + .catch(e => logger.error('Failed to toggle like', {error: e})) + }, [item]) const onCopyPostText = React.useCallback(() => { Clipboard.setString(record.text) @@ -169,9 +170,9 @@ const PostLoaded = observer(function PostLoadedImpl({ Toast.show('You will now receive notifications for this thread') } } catch (e) { - store.log.error('Failed to toggle thread mute', {error: e}) + logger.error('Failed to toggle thread mute', {error: e}) } - }, [item, store]) + }, [item]) const onDeletePost = React.useCallback(() => { item.delete().then( @@ -180,11 +181,11 @@ const PostLoaded = observer(function PostLoadedImpl({ Toast.show('Post deleted') }, e => { - store.log.error('Failed to delete post', {error: e}) + logger.error('Failed to delete post', {error: e}) Toast.show('Failed to delete post, please try again') }, ) - }, [item, setDeleted, store]) + }, [item, setDeleted]) const onPressShowMore = React.useCallback(() => { setLimitLines(false) diff --git a/src/view/com/posts/Feed.tsx b/src/view/com/posts/Feed.tsx index 7d54fd84..1ecb1491 100644 --- a/src/view/com/posts/Feed.tsx +++ b/src/view/com/posts/Feed.tsx @@ -19,6 +19,7 @@ import {s} from 'lib/styles' import {useAnalytics} from 'lib/analytics/analytics' import {usePalette} from 'lib/hooks/usePalette' import {useTheme} from 'lib/ThemeContext' +import {logger} from '#/logger' const LOADING_ITEM = {_reactKey: '__loading__'} const EMPTY_FEED_ITEM = {_reactKey: '__empty__'} @@ -92,7 +93,7 @@ export const Feed = observer(function Feed({ try { await feed.refresh() } catch (err) { - feed.rootStore.log.error('Failed to refresh posts feed', {error: err}) + logger.error('Failed to refresh posts feed', {error: err}) } setIsRefreshing(false) }, [feed, track, setIsRefreshing]) @@ -104,7 +105,7 @@ export const Feed = observer(function Feed({ try { await feed.loadMore() } catch (err) { - feed.rootStore.log.error('Failed to load more posts', {error: err}) + logger.error('Failed to load more posts', {error: err}) } }, [feed, track]) diff --git a/src/view/com/posts/FeedErrorMessage.tsx b/src/view/com/posts/FeedErrorMessage.tsx index 52fa9246..9e75d950 100644 --- a/src/view/com/posts/FeedErrorMessage.tsx +++ b/src/view/com/posts/FeedErrorMessage.tsx @@ -10,6 +10,7 @@ import {usePalette} from 'lib/hooks/usePalette' import {useNavigation} from '@react-navigation/native' import {NavigationProp} from 'lib/routes/types' import {useStores} from 'state/index' +import {logger} from '#/logger' const MESSAGES = { [KnownError.Unknown]: '', @@ -73,7 +74,7 @@ function FeedgenErrorMessage({ Toast.show( 'There was an an issue removing this feed. Please check your internet connection and try again.', ) - store.log.error('Failed to remove feed', {error: err}) + logger.error('Failed to remove feed', {error: err}) } }, onPressCancel() { diff --git a/src/view/com/posts/FeedItem.tsx b/src/view/com/posts/FeedItem.tsx index 4d49eba6..aeee3e20 100644 --- a/src/view/com/posts/FeedItem.tsx +++ b/src/view/com/posts/FeedItem.tsx @@ -32,6 +32,7 @@ import {makeProfileLink} from 'lib/routes/links' import {isEmbedByEmbedder} from 'lib/embeds' import {MAX_POST_LINES} from 'lib/constants' import {countLines} from 'lib/strings/helpers' +import {logger} from '#/logger' export const FeedItem = observer(function FeedItemImpl({ item, @@ -94,15 +95,15 @@ export const FeedItem = observer(function FeedItemImpl({ track('FeedItem:PostRepost') return item .toggleRepost() - .catch(e => store.log.error('Failed to toggle repost', {error: e})) - }, [track, item, store]) + .catch(e => logger.error('Failed to toggle repost', {error: e})) + }, [track, item]) const onPressToggleLike = React.useCallback(() => { track('FeedItem:PostLike') return item .toggleLike() - .catch(e => store.log.error('Failed to toggle like', {error: e})) - }, [track, item, store]) + .catch(e => logger.error('Failed to toggle like', {error: e})) + }, [track, item]) const onCopyPostText = React.useCallback(() => { Clipboard.setString(record?.text || '') @@ -123,9 +124,9 @@ export const FeedItem = observer(function FeedItemImpl({ Toast.show('You will now receive notifications for this thread') } } catch (e) { - store.log.error('Failed to toggle thread mute', {error: e}) + logger.error('Failed to toggle thread mute', {error: e}) } - }, [track, item, store]) + }, [track, item]) const onDeletePost = React.useCallback(() => { track('FeedItem:PostDelete') @@ -135,11 +136,11 @@ export const FeedItem = observer(function FeedItemImpl({ Toast.show('Post deleted') }, e => { - store.log.error('Failed to delete post', {error: e}) + logger.error('Failed to delete post', {error: e}) Toast.show('Failed to delete post, please try again') }, ) - }, [track, item, setDeleted, store]) + }, [track, item, setDeleted]) const onPressShowMore = React.useCallback(() => { setLimitLines(false) diff --git a/src/view/com/profile/ProfileFollowers.tsx b/src/view/com/profile/ProfileFollowers.tsx index 7e41b131..00ea48ed 100644 --- a/src/view/com/profile/ProfileFollowers.tsx +++ b/src/view/com/profile/ProfileFollowers.tsx @@ -10,6 +10,7 @@ import {ErrorMessage} from '../util/error/ErrorMessage' import {ProfileCardWithFollowBtn} from './ProfileCard' import {useStores} from 'state/index' import {usePalette} from 'lib/hooks/usePalette' +import {logger} from '#/logger' export const ProfileFollowers = observer(function ProfileFollowers({ name, @@ -27,16 +28,16 @@ export const ProfileFollowers = observer(function ProfileFollowers({ view .loadMore() .catch(err => - store.log.error('Failed to fetch user followers', {error: err}), + logger.error('Failed to fetch user followers', {error: err}), ) - }, [view, store.log]) + }, [view]) const onRefresh = () => { view.refresh() } const onEndReached = () => { view.loadMore().catch(err => - view?.rootStore.log.error('Failed to load more followers', { + logger.error('Failed to load more followers', { error: err, }), ) diff --git a/src/view/com/profile/ProfileFollows.tsx b/src/view/com/profile/ProfileFollows.tsx index 22722ee6..abc35398 100644 --- a/src/view/com/profile/ProfileFollows.tsx +++ b/src/view/com/profile/ProfileFollows.tsx @@ -7,6 +7,7 @@ import {ErrorMessage} from '../util/error/ErrorMessage' import {ProfileCardWithFollowBtn} from './ProfileCard' import {useStores} from 'state/index' import {usePalette} from 'lib/hooks/usePalette' +import {logger} from '#/logger' export const ProfileFollows = observer(function ProfileFollows({ name, @@ -23,8 +24,8 @@ export const ProfileFollows = observer(function ProfileFollows({ useEffect(() => { view .loadMore() - .catch(err => store.log.error('Failed to fetch user follows', err)) - }, [view, store.log]) + .catch(err => logger.error('Failed to fetch user follows', err)) + }, [view]) const onRefresh = () => { view.refresh() @@ -32,9 +33,7 @@ export const ProfileFollows = observer(function ProfileFollows({ const onEndReached = () => { view .loadMore() - .catch(err => - view?.rootStore.log.error('Failed to load more follows', err), - ) + .catch(err => logger.error('Failed to load more follows', err)) } if (!view.hasLoaded) { diff --git a/src/view/com/profile/ProfileHeader.tsx b/src/view/com/profile/ProfileHeader.tsx index d4fd88ca..1a1d38e4 100644 --- a/src/view/com/profile/ProfileHeader.tsx +++ b/src/view/com/profile/ProfileHeader.tsx @@ -39,6 +39,7 @@ import {isInvalidHandle} from 'lib/strings/handles' import {makeProfileLink} from 'lib/routes/links' import {Link} from '../util/Link' import {ProfileHeaderSuggestedFollows} from './ProfileHeaderSuggestedFollows' +import {logger} from '#/logger' interface Props { view: ProfileModel @@ -150,9 +151,9 @@ const ProfileHeaderLoaded = observer(function ProfileHeaderLoadedImpl({ : 'ProfileHeader:UnfollowButtonClicked', ) }, - err => store.log.error('Failed to toggle follow', {error: err}), + err => logger.error('Failed to toggle follow', {error: err}), ) - }, [track, view, store.log, setShowSuggestedFollows]) + }, [track, view, setShowSuggestedFollows]) const onPressEditProfile = React.useCallback(() => { track('ProfileHeader:EditProfileButtonClicked') @@ -193,10 +194,10 @@ const ProfileHeaderLoaded = observer(function ProfileHeaderLoadedImpl({ await view.muteAccount() Toast.show('Account muted') } catch (e: any) { - store.log.error('Failed to mute account', {error: e}) + logger.error('Failed to mute account', {error: e}) Toast.show(`There was an issue! ${e.toString()}`) } - }, [track, view, store]) + }, [track, view]) const onPressUnmuteAccount = React.useCallback(async () => { track('ProfileHeader:UnmuteAccountButtonClicked') @@ -204,10 +205,10 @@ const ProfileHeaderLoaded = observer(function ProfileHeaderLoadedImpl({ await view.unmuteAccount() Toast.show('Account unmuted') } catch (e: any) { - store.log.error('Failed to unmute account', {error: e}) + logger.error('Failed to unmute account', {error: e}) Toast.show(`There was an issue! ${e.toString()}`) } - }, [track, view, store]) + }, [track, view]) const onPressBlockAccount = React.useCallback(async () => { track('ProfileHeader:BlockAccountButtonClicked') @@ -222,7 +223,7 @@ const ProfileHeaderLoaded = observer(function ProfileHeaderLoadedImpl({ onRefreshAll() Toast.show('Account blocked') } catch (e: any) { - store.log.error('Failed to block account', {error: e}) + logger.error('Failed to block account', {error: e}) Toast.show(`There was an issue! ${e.toString()}`) } }, @@ -242,7 +243,7 @@ const ProfileHeaderLoaded = observer(function ProfileHeaderLoadedImpl({ onRefreshAll() Toast.show('Account unblocked') } catch (e: any) { - store.log.error('Failed to unblock account', {error: e}) + logger.error('Failed to unblock account', {error: e}) Toast.show(`There was an issue! ${e.toString()}`) } }, diff --git a/src/view/screens/ModerationBlockedAccounts.tsx b/src/view/screens/ModerationBlockedAccounts.tsx index a32c5e36..f302c96b 100644 --- a/src/view/screens/ModerationBlockedAccounts.tsx +++ b/src/view/screens/ModerationBlockedAccounts.tsx @@ -21,6 +21,7 @@ import {useFocusEffect} from '@react-navigation/native' import {ViewHeader} from '../com/util/ViewHeader' import {CenteredView} from 'view/com/util/Views' import {ProfileCard} from 'view/com/profile/ProfileCard' +import {logger} from '#/logger' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -52,9 +53,9 @@ export const ModerationBlockedAccounts = withAuthRequired( blockedAccounts .loadMore() .catch(err => - store.log.error('Failed to load more blocked accounts', {error: err}), + logger.error('Failed to load more blocked accounts', {error: err}), ) - }, [blockedAccounts, store]) + }, [blockedAccounts]) const renderItem = ({ item, diff --git a/src/view/screens/ModerationMutedAccounts.tsx b/src/view/screens/ModerationMutedAccounts.tsx index 61911717..20bd21f3 100644 --- a/src/view/screens/ModerationMutedAccounts.tsx +++ b/src/view/screens/ModerationMutedAccounts.tsx @@ -21,6 +21,7 @@ import {useFocusEffect} from '@react-navigation/native' import {ViewHeader} from '../com/util/ViewHeader' import {CenteredView} from 'view/com/util/Views' import {ProfileCard} from 'view/com/profile/ProfileCard' +import {logger} from '#/logger' type Props = NativeStackScreenProps< CommonNavigatorParams, @@ -49,9 +50,9 @@ export const ModerationMutedAccounts = withAuthRequired( mutedAccounts .loadMore() .catch(err => - store.log.error('Failed to load more muted accounts', {error: err}), + logger.error('Failed to load more muted accounts', {error: err}), ) - }, [mutedAccounts, store]) + }, [mutedAccounts]) const renderItem = ({ item, diff --git a/src/view/screens/Notifications.tsx b/src/view/screens/Notifications.tsx index b00bfb76..e1137ae9 100644 --- a/src/view/screens/Notifications.tsx +++ b/src/view/screens/Notifications.tsx @@ -20,6 +20,7 @@ import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' import {s, colors} from 'lib/styles' import {useAnalytics} from 'lib/analytics/analytics' import {isWeb} from 'platform/detection' +import {logger} from '#/logger' type Props = NativeStackScreenProps< NotificationsTabNavigatorParams, @@ -60,7 +61,7 @@ export const NotificationsScreen = withAuthRequired( useFocusEffect( React.useCallback(() => { store.shell.setMinimalShellMode(false) - store.log.debug('NotificationsScreen: Updating feed') + logger.debug('NotificationsScreen: Updating feed') const softResetSub = store.onScreenSoftReset(onPressLoadLatest) store.me.notifications.update() screen('Notifications') diff --git a/src/view/screens/PostThread.tsx b/src/view/screens/PostThread.tsx index 5f15adcc..8bb279be 100644 --- a/src/view/screens/PostThread.tsx +++ b/src/view/screens/PostThread.tsx @@ -14,6 +14,7 @@ import {s} from 'lib/styles' import {useSafeAreaInsets} from 'react-native-safe-area-context' import {clamp} from 'lodash' import {useWebMediaQueries} from 'lib/hooks/useWebMediaQueries' +import {logger} from '#/logger' const SHELL_FOOTER_HEIGHT = 44 @@ -38,7 +39,7 @@ export const PostThreadScreen = withAuthRequired( InteractionManager.runAfterInteractions(() => { if (!view.hasLoaded && !view.isLoading) { view.setup().catch(err => { - store.log.error('Failed to fetch thread', {error: err}) + logger.error('Failed to fetch thread', {error: err}) }) } }) diff --git a/src/view/screens/Profile.tsx b/src/view/screens/Profile.tsx index d353c411..f183ebbc 100644 --- a/src/view/screens/Profile.tsx +++ b/src/view/screens/Profile.tsx @@ -29,6 +29,7 @@ import {FeedSourceCard} from 'view/com/feeds/FeedSourceCard' import {FeedSourceModel} from 'state/models/content/feed-source' import {useSetTitle} from 'lib/hooks/useSetTitle' import {combinedDisplayName} from 'lib/strings/display-names' +import {logger} from '#/logger' type Props = NativeStackScreenProps export const ProfileScreen = withAuthRequired( @@ -108,16 +109,16 @@ export const ProfileScreen = withAuthRequired( uiState .refresh() .catch((err: any) => - store.log.error('Failed to refresh user profile', {error: err}), + logger.error('Failed to refresh user profile', {error: err}), ) - }, [uiState, store]) + }, [uiState]) const onEndReached = React.useCallback(() => { uiState.loadMore().catch((err: any) => - store.log.error('Failed to load more entries in user profile', { + logger.error('Failed to load more entries in user profile', { error: err, }), ) - }, [uiState, store]) + }, [uiState]) const onPressTryAgain = React.useCallback(() => { uiState.setup() }, [uiState]) diff --git a/src/view/screens/ProfileFeed.tsx b/src/view/screens/ProfileFeed.tsx index 253031ff..6a3da665 100644 --- a/src/view/screens/ProfileFeed.tsx +++ b/src/view/screens/ProfileFeed.tsx @@ -40,6 +40,7 @@ import {NavigationProp} from 'lib/routes/types' import {sanitizeHandle} from 'lib/strings/handles' import {makeProfileLink} from 'lib/routes/links' import {ComposeIcon2} from 'lib/icons' +import {logger} from '#/logger' const SECTION_TITLES = ['Posts', 'About'] @@ -165,9 +166,9 @@ export const ProfileFeedScreenInner = observer( Toast.show( 'There was an an issue updating your feeds, please check your internet connection and try again.', ) - store.log.error('Failed up update feeds', {error: err}) + logger.error('Failed up update feeds', {error: err}) } - }, [store, feedInfo]) + }, [feedInfo]) const onToggleLiked = React.useCallback(async () => { Haptics.default() @@ -181,19 +182,19 @@ export const ProfileFeedScreenInner = observer( Toast.show( 'There was an an issue contacting the server, please check your internet connection and try again.', ) - store.log.error('Failed up toggle like', {error: err}) + logger.error('Failed up toggle like', {error: err}) } - }, [store, feedInfo]) + }, [feedInfo]) const onTogglePinned = React.useCallback(async () => { Haptics.default() if (feedInfo) { feedInfo.togglePin().catch(e => { Toast.show('There was an issue contacting the server') - store.log.error('Failed to toggle pinned feed', {error: e}) + logger.error('Failed to toggle pinned feed', {error: e}) }) } - }, [store, feedInfo]) + }, [feedInfo]) const onPressShare = React.useCallback(() => { const url = toShareUrl(`/profile/${handleOrDid}/feed/${rkey}`) diff --git a/src/view/screens/ProfileList.tsx b/src/view/screens/ProfileList.tsx index 7580dcf5..cfe9c418 100644 --- a/src/view/screens/ProfileList.tsx +++ b/src/view/screens/ProfileList.tsx @@ -43,6 +43,7 @@ import {sanitizeHandle} from 'lib/strings/handles' import {makeProfileLink, makeListLink} from 'lib/routes/links' import {ComposeIcon2} from 'lib/icons' import {ListItems} from 'view/com/lists/ListItems' +import {logger} from '#/logger' const SECTION_TITLES_CURATE = ['Posts', 'About'] const SECTION_TITLES_MOD = ['About'] @@ -272,9 +273,9 @@ const Header = observer(function HeaderImpl({ Haptics.default() list.togglePin().catch(e => { Toast.show('There was an issue contacting the server') - store.log.error('Failed to toggle pinned list', {error: e}) + logger.error('Failed to toggle pinned list', {error: e}) }) - }, [store, list]) + }, [list]) const onSubscribeMute = useCallback(() => { store.shell.openModal({ diff --git a/src/view/screens/SavedFeeds.tsx b/src/view/screens/SavedFeeds.tsx index 900bb06a..18bbf06c 100644 --- a/src/view/screens/SavedFeeds.tsx +++ b/src/view/screens/SavedFeeds.tsx @@ -26,6 +26,7 @@ import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' import * as Toast from 'view/com/util/Toast' import {Haptics} from 'lib/haptics' import {TextLink} from 'view/com/util/Link' +import {logger} from '#/logger' const HITSLOP_TOP = { top: 20, @@ -159,31 +160,30 @@ const ListItem = observer(function ListItemImpl({ item: FeedSourceModel }) { const pal = usePalette('default') - const store = useStores() const isPinned = item.isPinned const onTogglePinned = useCallback(() => { Haptics.default() item.togglePin().catch(e => { Toast.show('There was an issue contacting the server') - store.log.error('Failed to toggle pinned feed', {error: e}) + logger.error('Failed to toggle pinned feed', {error: e}) }) - }, [item, store]) + }, [item]) const onPressUp = useCallback( () => savedFeeds.movePinnedFeed(item, 'up').catch(e => { Toast.show('There was an issue contacting the server') - store.log.error('Failed to set pinned feed order', {error: e}) + logger.error('Failed to set pinned feed order', {error: e}) }), - [store, savedFeeds, item], + [savedFeeds, item], ) const onPressDown = useCallback( () => savedFeeds.movePinnedFeed(item, 'down').catch(e => { Toast.show('There was an issue contacting the server') - store.log.error('Failed to set pinned feed order', {error: e}) + logger.error('Failed to set pinned feed order', {error: e}) }), - [store, savedFeeds, item], + [savedFeeds, item], ) return ( diff --git a/src/view/screens/Settings.tsx b/src/view/screens/Settings.tsx index c2c6d1ef..3f498ba8 100644 --- a/src/view/screens/Settings.tsx +++ b/src/view/screens/Settings.tsx @@ -45,6 +45,7 @@ import {formatCount} from 'view/com/util/numeric/format' import Clipboard from '@react-native-clipboard/clipboard' import {makeProfileLink} from 'lib/routes/links' import {AccountDropdownBtn} from 'view/com/util/AccountDropdownBtn' +import {logger} from '#/logger' // TEMPORARY (APP-700) // remove after backend testing finishes @@ -110,10 +111,9 @@ export const SettingsScreen = withAuthRequired( Toast.show('Your handle has been updated') }, err => { - store.log.error( - 'Failed to reload from server after handle update', - {error: err}, - ) + logger.error('Failed to reload from server after handle update', { + error: err, + }) setIsSwitching(false) }, )