Upgrade prettier to 3.6 (#8558)

* upgrade prettier

* run prettier

* more files
This commit is contained in:
Samuel Newman
2025-06-23 17:44:40 +03:00
committed by GitHub
parent 3c92714e4e
commit c634cd9071
60 changed files with 427 additions and 383 deletions
+2 -2
View File
@@ -29,8 +29,8 @@ module.exports = function (_config) {
const UPDATES_CHANNEL = IS_TESTFLIGHT const UPDATES_CHANNEL = IS_TESTFLIGHT
? 'testflight' ? 'testflight'
: IS_PRODUCTION : IS_PRODUCTION
? 'production' ? 'production'
: undefined : undefined
const UPDATES_ENABLED = !!UPDATES_CHANNEL const UPDATES_ENABLED = !!UPDATES_CHANNEL
const USE_SENTRY = Boolean(process.env.SENTRY_AUTH_TOKEN) const USE_SENTRY = Boolean(process.env.SENTRY_AUTH_TOKEN)
+1 -3
View File
@@ -1,9 +1,7 @@
/** @type {import('tailwindcss').Config} */ /** @type {import('tailwindcss').Config} */
module.exports = { module.exports = {
content: ['./index.html', './src/**/*.{js,ts,jsx,tsx}'], content: ['./index.html', './src/**/*.{js,ts,jsx,tsx}'],
darkMode: ['variant', [ darkMode: ['variant', ['&:is(.dark *):not(:is(.dark .light *))']],
'&:is(.dark *):not(:is(.dark .light *))',
]],
theme: { theme: {
extend: { extend: {
colors: { colors: {
-1
View File
@@ -1,4 +1,3 @@
{ {
"compilerOptions": { "compilerOptions": {
"target": "ES5", "target": "ES5",
+11 -8
View File
@@ -1,27 +1,30 @@
import assert from 'assert' import assert from 'assert'
import { import {
Kysely, Kysely,
KyselyPlugin, type KyselyPlugin,
Migrator, Migrator,
PluginTransformQueryArgs, type PluginTransformQueryArgs,
PluginTransformResultArgs, type PluginTransformResultArgs,
PostgresDialect, PostgresDialect,
QueryResult, type QueryResult,
RootOperationNode, type RootOperationNode,
UnknownRow, type UnknownRow,
} from 'kysely' } from 'kysely'
import {default as Pg} from 'pg' import {default as Pg} from 'pg'
import {dbLogger as log} from '../logger.js' import {dbLogger as log} from '../logger.js'
import {default as migrations} from './migrations/index.js' import {default as migrations} from './migrations/index.js'
import {DbMigrationProvider} from './migrations/provider.js' import {DbMigrationProvider} from './migrations/provider.js'
import {DbSchema} from './schema.js' import {type DbSchema} from './schema.js'
export class Database { export class Database {
migrator: Migrator migrator: Migrator
destroyed = false destroyed = false
constructor(public db: Kysely<DbSchema>, public cfg: PgConfig) { constructor(
public db: Kysely<DbSchema>,
public cfg: PgConfig,
) {
this.migrator = new Migrator({ this.migrator = new Migrator({
db, db,
migrationTableSchema: cfg.schema, migrationTableSchema: cfg.schema,
+7 -4
View File
@@ -1,11 +1,11 @@
import events from 'node:events' import events from 'node:events'
import http from 'node:http' import type http from 'node:http'
import cors from 'cors' import cors from 'cors'
import express from 'express' import express from 'express'
import {createHttpTerminator, HttpTerminator} from 'http-terminator' import {createHttpTerminator, type HttpTerminator} from 'http-terminator'
import {Config} from './config.js' import {type Config} from './config.js'
import {AppContext} from './context.js' import {AppContext} from './context.js'
import {default as routes, errorHandler} from './routes/index.js' import {default as routes, errorHandler} from './routes/index.js'
@@ -17,7 +17,10 @@ export class LinkService {
public server?: http.Server public server?: http.Server
private terminator?: HttpTerminator private terminator?: HttpTerminator
constructor(public app: express.Application, public ctx: AppContext) {} constructor(
public app: express.Application,
public ctx: AppContext,
) {}
static async create(cfg: Config): Promise<LinkService> { static async create(cfg: Config): Promise<LinkService> {
let app = express() let app = express()
+7 -4
View File
@@ -1,10 +1,10 @@
import events from 'node:events' import events from 'node:events'
import http from 'node:http' import type http from 'node:http'
import express from 'express' import express from 'express'
import {createHttpTerminator, HttpTerminator} from 'http-terminator' import {createHttpTerminator, type HttpTerminator} from 'http-terminator'
import {Config} from './config.js' import {type Config} from './config.js'
import {AppContext} from './context.js' import {AppContext} from './context.js'
import {default as routes, errorHandler} from './routes/index.js' import {default as routes, errorHandler} from './routes/index.js'
@@ -15,7 +15,10 @@ export class CardService {
public server?: http.Server public server?: http.Server
private terminator?: HttpTerminator private terminator?: HttpTerminator
constructor(public app: express.Application, public ctx: AppContext) {} constructor(
public app: express.Application,
public ctx: AppContext,
) {}
static async create(cfg: Config): Promise<CardService> { static async create(cfg: Config): Promise<CardService> {
let app = express() let app = express()
@@ -12,7 +12,7 @@ const EmojiPicker = ({onEmojiSelected}: EmojiPickerViewProps) => {
flex: 1, flex: 1,
width: '100%', width: '100%',
backgroundColor: scheme === 'dark' ? '#000' : '#fff', backgroundColor: scheme === 'dark' ? '#000' : '#fff',
} as const), }) as const,
[scheme], [scheme],
) )
+1 -1
View File
@@ -266,7 +266,7 @@
"lint-staged": "^13.2.3", "lint-staged": "^13.2.3",
"lockfile-lint": "^4.14.0", "lockfile-lint": "^4.14.0",
"metro-react-native-babel-preset": "^0.77.0", "metro-react-native-babel-preset": "^0.77.0",
"prettier": "^2.8.3", "prettier": "^3.6.0",
"react-native-dotenv": "^3.4.11", "react-native-dotenv": "^3.4.11",
"react-refresh": "^0.14.0", "react-refresh": "^0.14.0",
"svgo": "^3.3.2", "svgo": "^3.3.2",
+3 -4
View File
@@ -9,10 +9,9 @@ const templateFile = path.join(
'scripts.html', 'scripts.html',
) )
const {entrypoints} = require(path.join( const {entrypoints} = require(
projectRoot, path.join(projectRoot, 'web-build/asset-manifest.json'),
'web-build/asset-manifest.json', )
))
console.log(`Found ${entrypoints.length} entrypoints`) console.log(`Found ${entrypoints.length} entrypoints`)
console.log(`Writing ${templateFile}`) console.log(`Writing ${templateFile}`)
+3 -3
View File
@@ -190,7 +190,7 @@ export function Root({children}: {children: React.ReactNode}) {
if (item) playHaptic('Light') if (item) playHaptic('Light')
setHoveredMenuItem(item) setHoveredMenuItem(item)
}, },
} satisfies ContextType), }) satisfies ContextType,
[ [
measurement, measurement,
setMeasurement, setMeasurement,
@@ -710,8 +710,8 @@ export function Item({
const xOffset = position const xOffset = position
? position.x ? position.x
: align === 'left' : align === 'left'
? measurement.x ? measurement.x
: measurement.x + measurement.width - layout.width : measurement.x + measurement.width - layout.width
registerHoverable( registerHoverable(
id, id,
+4 -4
View File
@@ -99,10 +99,10 @@ export function useLink({
return typeof to === 'string' return typeof to === 'string'
? convertBskyAppUrlIfNeeded(sanitizeUrl(to)) ? convertBskyAppUrlIfNeeded(sanitizeUrl(to))
: to.screen : to.screen
? router.matchName(to.screen)?.build(to.params) ? router.matchName(to.screen)?.build(to.params)
: to.href : to.href
? convertBskyAppUrlIfNeeded(sanitizeUrl(to.href)) ? convertBskyAppUrlIfNeeded(sanitizeUrl(to.href))
: undefined : undefined
}, [to]) }, [to])
if (!href) { if (!href) {
+3 -3
View File
@@ -77,9 +77,9 @@ export function ImageEmbed({
rest.viewContext === PostEmbedViewContext.ThreadHighlighted rest.viewContext === PostEmbedViewContext.ThreadHighlighted
? 'none' ? 'none'
: rest.viewContext === : rest.viewContext ===
PostEmbedViewContext.FeedEmbedRecordWithMedia PostEmbedViewContext.FeedEmbedRecordWithMedia
? 'square' ? 'square'
: 'constrained' : 'constrained'
} }
image={image} image={image}
onPress={(containerRef, dims) => onPress(0, [containerRef], [dims])} onPress={(containerRef, dims) => onPress(0, [containerRef], [dims])}
@@ -317,8 +317,8 @@ export function Controls({
!focused !focused
? msg`Unmute video` ? msg`Unmute video`
: playing : playing
? msg`Pause video` ? msg`Pause video`
: msg`Play video`, : msg`Play video`,
)} )}
accessibilityHint="" accessibilityHint=""
style={[ style={[
@@ -600,8 +600,8 @@ let PostMenuItems = ({
isDetachPending isDetachPending
? Loader ? Loader
: quoteEmbed.isDetached : quoteEmbed.isDetached
? Eye ? Eye
: EyeSlash : EyeSlash
} }
position="right" position="right"
/> />
+2 -2
View File
@@ -111,8 +111,8 @@ export function Trigger({children, label}: TriggerProps) {
borderColor: focused borderColor: focused
? t.palette.primary_500 ? t.palette.primary_500
: hovered : hovered
? t.palette.contrast_100 ? t.palette.contrast_100
: t.palette.contrast_25, : t.palette.contrast_25,
}, },
])}> ])}>
{children} {children}
+12 -6
View File
@@ -1,9 +1,15 @@
import React from 'react' import React from 'react'
import {Keyboard, Platform, StyleProp, View, ViewStyle} from 'react-native'
import { import {
AppBskyFeedDefs, Keyboard,
Platform,
type StyleProp,
View,
type ViewStyle,
} from 'react-native'
import {
type AppBskyFeedDefs,
AppBskyFeedPost, AppBskyFeedPost,
AppBskyGraphDefs, type AppBskyGraphDefs,
AtUri, AtUri,
} from '@atproto/api' } from '@atproto/api'
import {msg, Trans} from '@lingui/macro' import {msg, Trans} from '@lingui/macro'
@@ -13,7 +19,7 @@ import {HITSLOP_10} from '#/lib/constants'
import {makeListLink, makeProfileLink} from '#/lib/routes/links' import {makeListLink, makeProfileLink} from '#/lib/routes/links'
import {isNative} from '#/platform/detection' import {isNative} from '#/platform/detection'
import { import {
ThreadgateAllowUISetting, type ThreadgateAllowUISetting,
threadgateViewToAllowUISetting, threadgateViewToAllowUISetting,
} from '#/state/queries/threadgate' } from '#/state/queries/threadgate'
import {atoms as a, useTheme} from '#/alf' import {atoms as a, useTheme} from '#/alf'
@@ -70,8 +76,8 @@ export function WhoCanReply({post, isThreadAuthor, style}: WhoCanReplyProps) {
const description = anyoneCanReply const description = anyoneCanReply
? _(msg`Everybody can reply`) ? _(msg`Everybody can reply`)
: noOneCanReply : noOneCanReply
? _(msg`Replies disabled`) ? _(msg`Replies disabled`)
: _(msg`Some people can reply`) : _(msg`Some people can reply`)
const onPressOpen = () => { const onPressOpen = () => {
if (isNative && Keyboard.isVisible()) { if (isNative && Keyboard.isVisible()) {
@@ -185,8 +185,8 @@ export function Disable() {
state.emailStatus === 'pending' state.emailStatus === 'pending'
? Loader ? Loader
: state.emailStatus === 'success' : state.emailStatus === 'success'
? Check ? Check
: Envelope : Envelope
} }
/> />
</Button> </Button>
@@ -116,8 +116,8 @@ export function Enable() {
state.status === 'pending' state.status === 'pending'
? Loader ? Loader
: state.status === 'success' : state.status === 'success'
? Check ? Check
: ShieldIcon : ShieldIcon
} }
/> />
</Button> </Button>
@@ -390,8 +390,8 @@ function DefaultProfileCard({
!enabled !enabled
? {opacity: 0.5} ? {opacity: 0.5}
: pressed || focused || hovered : pressed || focused || hovered
? t.atoms.bg_contrast_25 ? t.atoms.bg_contrast_25
: t.atoms.bg, : t.atoms.bg,
]}> ]}>
<ProfileCard.Header> <ProfileCard.Header>
<ProfileCard.Avatar <ProfileCard.Avatar
+2 -2
View File
@@ -98,8 +98,8 @@ export function EmojiReactionPicker({
: t.palette.primary_500, : t.palette.primary_500,
} }
: alreadyReacted : alreadyReacted
? {backgroundColor: t.palette.primary_200} ? {backgroundColor: t.palette.primary_200}
: bgColor, : bgColor,
{height: 40, width: 40}, {height: 40, width: 40},
a.justify_center, a.justify_center,
a.align_center, a.align_center,
+1 -2
View File
@@ -128,8 +128,7 @@ export let MessageContextMenu = ({
label={_(msg`Message options`)} label={_(msg`Message options`)}
contentLabel={_( contentLabel={_(
msg`Message from @${ msg`Message from @${
sender?.handle ?? // should always be defined sender?.handle ?? 'unknown' // should always be defined
'unknown'
}: ${message.text}`, }: ${message.text}`,
)}> )}>
{children} {children}
+23 -24
View File
@@ -3,28 +3,27 @@ import Svg, {Circle, Path} from 'react-native-svg'
import {type Props, useCommonSVGProps} from '#/components/icons/common' import {type Props, useCommonSVGProps} from '#/components/icons/common'
export const VerifiedCheck = React.forwardRef<Svg, Props>(function LogoImpl( export const VerifiedCheck = React.forwardRef<Svg, Props>(
props, function LogoImpl(props, ref) {
ref, const {fill, size, style, ...rest} = useCommonSVGProps(props)
) {
const {fill, size, style, ...rest} = useCommonSVGProps(props)
return ( return (
<Svg <Svg
fill="none" fill="none"
{...rest} {...rest}
ref={ref} ref={ref}
viewBox="0 0 24 24" viewBox="0 0 24 24"
width={size} width={size}
height={size} height={size}
style={[style]}> style={[style]}>
<Circle cx="12" cy="12" r="11.5" fill={fill} /> <Circle cx="12" cy="12" r="11.5" fill={fill} />
<Path <Path
fill="#fff" fill="#fff"
fillRule="evenodd" fillRule="evenodd"
clipRule="evenodd" clipRule="evenodd"
d="M17.659 8.175a1.361 1.361 0 0 1 0 1.925l-6.224 6.223a1.361 1.361 0 0 1-1.925 0L6.4 13.212a1.361 1.361 0 0 1 1.925-1.925l2.149 2.148 5.26-5.26a1.361 1.361 0 0 1 1.925 0Z" d="M17.659 8.175a1.361 1.361 0 0 1 0 1.925l-6.224 6.223a1.361 1.361 0 0 1-1.925 0L6.4 13.212a1.361 1.361 0 0 1 1.925-1.925l2.149 2.148 5.26-5.26a1.361 1.361 0 0 1 1.925 0Z"
/> />
</Svg> </Svg>
) )
}) },
)
+28 -29
View File
@@ -3,33 +3,32 @@ import Svg, {Path} from 'react-native-svg'
import {type Props, useCommonSVGProps} from '#/components/icons/common' import {type Props, useCommonSVGProps} from '#/components/icons/common'
export const VerifierCheck = React.forwardRef<Svg, Props>(function LogoImpl( export const VerifierCheck = React.forwardRef<Svg, Props>(
props, function LogoImpl(props, ref) {
ref, const {fill, size, style, ...rest} = useCommonSVGProps(props)
) {
const {fill, size, style, ...rest} = useCommonSVGProps(props)
return ( return (
<Svg <Svg
fill="none" fill="none"
{...rest} {...rest}
ref={ref} ref={ref}
viewBox="0 0 24 24" viewBox="0 0 24 24"
width={size} width={size}
height={size} height={size}
style={[style]}> style={[style]}>
<Path <Path
fill={fill} fill={fill}
fillRule="evenodd" fillRule="evenodd"
clipRule="evenodd" clipRule="evenodd"
d="M8.792 1.615a4.154 4.154 0 0 1 6.416 0 4.154 4.154 0 0 0 3.146 1.515 4.154 4.154 0 0 1 4 5.017 4.154 4.154 0 0 0 .777 3.404 4.154 4.154 0 0 1-1.427 6.255 4.153 4.153 0 0 0-2.177 2.73 4.154 4.154 0 0 1-5.781 2.784 4.154 4.154 0 0 0-3.492 0 4.154 4.154 0 0 1-5.78-2.784 4.154 4.154 0 0 0-2.178-2.73A4.154 4.154 0 0 1 .87 11.551a4.154 4.154 0 0 0 .776-3.404A4.154 4.154 0 0 1 5.646 3.13a4.154 4.154 0 0 0 3.146-1.515Z" d="M8.792 1.615a4.154 4.154 0 0 1 6.416 0 4.154 4.154 0 0 0 3.146 1.515 4.154 4.154 0 0 1 4 5.017 4.154 4.154 0 0 0 .777 3.404 4.154 4.154 0 0 1-1.427 6.255 4.153 4.153 0 0 0-2.177 2.73 4.154 4.154 0 0 1-5.781 2.784 4.154 4.154 0 0 0-3.492 0 4.154 4.154 0 0 1-5.78-2.784 4.154 4.154 0 0 0-2.178-2.73A4.154 4.154 0 0 1 .87 11.551a4.154 4.154 0 0 0 .776-3.404A4.154 4.154 0 0 1 5.646 3.13a4.154 4.154 0 0 0 3.146-1.515Z"
/> />
<Path <Path
fill="#fff" fill="#fff"
fillRule="evenodd" fillRule="evenodd"
clipRule="evenodd" clipRule="evenodd"
d="M17.861 8.26a1.438 1.438 0 0 1 0 2.033l-6.571 6.571a1.437 1.437 0 0 1-2.033 0L5.97 13.58a1.438 1.438 0 0 1 2.033-2.033l2.27 2.269 5.554-5.555a1.437 1.437 0 0 1 2.033 0Z" d="M17.861 8.26a1.438 1.438 0 0 1 0 2.033l-6.571 6.571a1.437 1.437 0 0 1-2.033 0L5.97 13.58a1.438 1.438 0 0 1 2.033-2.033l2.27 2.269 5.554-5.555a1.437 1.437 0 0 1 2.033 0Z"
/> />
</Svg> </Svg>
) )
}) },
)
+4 -4
View File
@@ -1,6 +1,6 @@
import React from 'react' import React from 'react'
import {StyleProp, View, ViewStyle} from 'react-native' import {type StyleProp, View, type ViewStyle} from 'react-native'
import {ModerationUI} from '@atproto/api' import {type ModerationUI} from '@atproto/api'
import {msg, Trans} from '@lingui/macro' import {msg, Trans} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
@@ -148,8 +148,8 @@ function ContentHiderActive({
modui.noOverride modui.noOverride
? _(msg`Learn more about the moderation applied to this content`) ? _(msg`Learn more about the moderation applied to this content`)
: override : override
? _(msg`Hides the content`) ? _(msg`Hides the content`)
: _(msg`Shows the content`) : _(msg`Shows the content`)
}> }>
{state => ( {state => (
<View <View
@@ -512,13 +512,13 @@ function StepTitle({
backgroundColor: active backgroundColor: active
? t.palette.primary_500 ? t.palette.primary_500
: completed : completed
? t.palette.primary_100 ? t.palette.primary_100
: t.atoms.bg_contrast_25.backgroundColor, : t.atoms.bg_contrast_25.backgroundColor,
borderColor: active borderColor: active
? t.palette.primary_500 ? t.palette.primary_500
: completed : completed
? t.palette.primary_400 ? t.palette.primary_400
: t.atoms.border_contrast_low.borderColor, : t.atoms.border_contrast_low.borderColor,
}, },
]}> ]}>
{completed ? ( {completed ? (
@@ -533,8 +533,8 @@ function StepTitle({
color: active color: active
? 'white' ? 'white'
: completed : completed
? t.palette.primary_700 ? t.palette.primary_700
: t.atoms.text_contrast_medium.color, : t.atoms.text_contrast_medium.color,
fontVariant: ['tabular-nums'], fontVariant: ['tabular-nums'],
width: 24, width: 24,
height: 24, height: 24,
@@ -130,8 +130,8 @@ export function Badge({
verifiedByHidden verifiedByHidden
? t.atoms.bg_contrast_100.backgroundColor ? t.atoms.bg_contrast_100.backgroundColor
: state.profile.isVerified : state.profile.isVerified
? t.palette.primary_500 ? t.palette.primary_500
: t.atoms.bg_contrast_100.backgroundColor : t.atoms.bg_contrast_100.backgroundColor
} }
verifier={state.profile.role === 'verifier'} verifier={state.profile.role === 'verifier'}
/> />
@@ -64,13 +64,13 @@ function Inner({
? _(msg`You are verified`) ? _(msg`You are verified`)
: _(msg`Your verifications`) : _(msg`Your verifications`)
: state.profile.isVerified : state.profile.isVerified
? _(msg`${userName} is verified`) ? _(msg`${userName} is verified`)
: _( : _(
msg({ msg({
message: `${userName}'s verifications`, message: `${userName}'s verifications`,
comment: `Possessive, meaning "the verifications of {userName}"`, comment: `Possessive, meaning "the verifications of {userName}"`,
}), }),
) )
return ( return (
<Dialog.ScrollableInner <Dialog.ScrollableInner
+9 -9
View File
@@ -1,18 +1,18 @@
import React from 'react' import React from 'react'
import { import {
AppBskyLabelerDefs, type AppBskyLabelerDefs,
BskyAgent, BskyAgent,
ComAtprotoLabelDefs, type ComAtprotoLabelDefs,
InterpretedLabelValueDefinition, type InterpretedLabelValueDefinition,
LABELS, LABELS,
ModerationCause, type ModerationCause,
ModerationOpts, type ModerationOpts,
ModerationUI, type ModerationUI,
} from '@atproto/api' } from '@atproto/api'
import {sanitizeDisplayName} from '#/lib/strings/display-names' import {sanitizeDisplayName} from '#/lib/strings/display-names'
import {sanitizeHandle} from '#/lib/strings/handles' import {sanitizeHandle} from '#/lib/strings/handles'
import {AppModerationCause} from '#/components/Pills' import {type AppModerationCause} from '#/components/Pills'
export const ADULT_CONTENT_LABELS = ['sexual', 'nudity', 'porn'] export const ADULT_CONTENT_LABELS = ['sexual', 'nudity', 'porn']
export const OTHER_SELF_LABELS = ['graphic-media'] export const OTHER_SELF_LABELS = ['graphic-media']
@@ -29,8 +29,8 @@ export function getModerationCauseKey(
cause.source.type === 'labeler' cause.source.type === 'labeler'
? cause.source.did ? cause.source.did
: cause.source.type === 'list' : cause.source.type === 'list'
? cause.source.list.uri ? cause.source.list.uri
: 'user' : 'user'
if (cause.type === 'label') { if (cause.type === 'label') {
return `label:${cause.label.val}:${source}` return `label:${cause.label.val}:${source}`
} }
@@ -1,8 +1,8 @@
import React from 'react' import React from 'react'
import { import {
BSKY_LABELER_DID, BSKY_LABELER_DID,
ModerationCause, type ModerationCause,
ModerationCauseSource, type ModerationCauseSource,
} from '@atproto/api' } from '@atproto/api'
import {msg} from '@lingui/macro' import {msg} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
@@ -12,10 +12,10 @@ import {useLabelDefinitions} from '#/state/preferences'
import {useSession} from '#/state/session' import {useSession} from '#/state/session'
import {CircleBanSign_Stroke2_Corner0_Rounded as CircleBanSign} from '#/components/icons/CircleBanSign' import {CircleBanSign_Stroke2_Corner0_Rounded as CircleBanSign} from '#/components/icons/CircleBanSign'
import {CircleInfo_Stroke2_Corner0_Rounded as CircleInfo} from '#/components/icons/CircleInfo' import {CircleInfo_Stroke2_Corner0_Rounded as CircleInfo} from '#/components/icons/CircleInfo'
import {Props as SVGIconProps} from '#/components/icons/common' import {type Props as SVGIconProps} from '#/components/icons/common'
import {EyeSlash_Stroke2_Corner0_Rounded as EyeSlash} from '#/components/icons/EyeSlash' import {EyeSlash_Stroke2_Corner0_Rounded as EyeSlash} from '#/components/icons/EyeSlash'
import {Warning_Stroke2_Corner0_Rounded as Warning} from '#/components/icons/Warning' import {Warning_Stroke2_Corner0_Rounded as Warning} from '#/components/icons/Warning'
import {AppModerationCause} from '#/components/Pills' import {type AppModerationCause} from '#/components/Pills'
import {useGlobalLabelStrings} from './useGlobalLabelStrings' import {useGlobalLabelStrings} from './useGlobalLabelStrings'
import {getDefinition, getLabelStrings} from './useLabelInfo' import {getDefinition, getLabelStrings} from './useLabelInfo'
@@ -153,8 +153,8 @@ export function useModerationCauseDescription(
def.identifier === '!no-unauthenticated' def.identifier === '!no-unauthenticated'
? EyeSlash ? EyeSlash
: def.severity === 'alert' : def.severity === 'alert'
? Warning ? Warning
: CircleInfo, : CircleInfo,
name: strings.name, name: strings.name,
description: strings.description, description: strings.description,
source, source,
+5 -5
View File
@@ -1,17 +1,17 @@
import React from 'react' import React from 'react'
import {Platform} from 'react-native' import {Platform} from 'react-native'
import {AppState, AppStateStatus} from 'react-native' import {AppState, type AppStateStatus} from 'react-native'
import {Statsig, StatsigProvider} from 'statsig-react-native-expo' import {Statsig, StatsigProvider} from 'statsig-react-native-expo'
import {BUNDLE_DATE, BUNDLE_IDENTIFIER, IS_TESTFLIGHT} from '#/lib/app-info' import {BUNDLE_DATE, BUNDLE_IDENTIFIER, IS_TESTFLIGHT} from '#/lib/app-info'
import {logger} from '#/logger' import {logger} from '#/logger'
import {MetricEvents} from '#/logger/metrics' import {type MetricEvents} from '#/logger/metrics'
import {isWeb} from '#/platform/detection' import {isWeb} from '#/platform/detection'
import * as persisted from '#/state/persisted' import * as persisted from '#/state/persisted'
import {useSession} from '../../state/session' import {useSession} from '../../state/session'
import {timeout} from '../async/timeout' import {timeout} from '../async/timeout'
import {useNonReactiveCallback} from '../hooks/useNonReactiveCallback' import {useNonReactiveCallback} from '../hooks/useNonReactiveCallback'
import {Gate} from './gates' import {type Gate} from './gates'
const SDK_KEY = 'client-SXJakO39w9vIhl3D44u8UupyzFl4oZ2qPIkjwcvuPsV' const SDK_KEY = 'client-SXJakO39w9vIhl3D44u8UupyzFl4oZ2qPIkjwcvuPsV'
@@ -51,8 +51,8 @@ function createStatsigOptions(prefetchUsers: StatsigUser[]) {
process.env.NODE_ENV === 'development' process.env.NODE_ENV === 'development'
? 'development' ? 'development'
: IS_TESTFLIGHT : IS_TESTFLIGHT
? 'staging' ? 'staging'
: 'production', : 'production',
}, },
// Don't block on waiting for network. The fetched config will kick in on next load. // Don't block on waiting for network. The fetched config will kick in on next load.
// This ensures the UI is always consistent and doesn't update mid-session. // This ensures the UI is always consistent and doesn't update mid-session.
+2 -2
View File
@@ -11,8 +11,8 @@ const IFRAME_HOST = isWeb
? 'http://localhost:8100' ? 'http://localhost:8100'
: 'https://bsky.app' : 'https://bsky.app'
: __DEV__ && !process.env.JEST_WORKER_ID : __DEV__ && !process.env.JEST_WORKER_ID
? 'http://localhost:8100' ? 'http://localhost:8100'
: 'https://bsky.app' : 'https://bsky.app'
export const embedPlayerSources = [ export const embedPlayerSources = [
'youtube', 'youtube',
+6 -6
View File
@@ -41,12 +41,12 @@ globalThis.atob = (str: string): string => {
r1 === 64 r1 === 64
? String.fromCharCode((bitmap >> 16) & 255) ? String.fromCharCode((bitmap >> 16) & 255)
: r2 === 64 : r2 === 64
? String.fromCharCode((bitmap >> 16) & 255, (bitmap >> 8) & 255) ? String.fromCharCode((bitmap >> 16) & 255, (bitmap >> 8) & 255)
: String.fromCharCode( : String.fromCharCode(
(bitmap >> 16) & 255, (bitmap >> 16) & 255,
(bitmap >> 8) & 255, (bitmap >> 8) & 255,
bitmap & 255, bitmap & 255,
) )
} }
return result return result
} }
+2 -2
View File
@@ -49,8 +49,8 @@ export const Login = ({onPressBack}: {onPressBack: () => void}) => {
requestedAccount requestedAccount
? Forms.Login ? Forms.Login
: accounts.length : accounts.length
? Forms.ChooseAccount ? Forms.ChooseAccount
: Forms.Login, : Forms.Login,
) )
const { const {
+1 -1
View File
@@ -155,7 +155,7 @@ export function MessagesScreen({navigation, route}: Props) {
profiles: inboxPreviewConvos.slice(0, 3), profiles: inboxPreviewConvos.slice(0, 3),
}, },
...conversations.map( ...conversations.map(
convo => ({type: 'CONVERSATION', conversation: convo} as const), convo => ({type: 'CONVERSATION', conversation: convo}) as const,
), ),
] satisfies ListItem[] ] satisfies ListItem[]
} }
+2 -2
View File
@@ -176,8 +176,8 @@ export function StepFinished() {
avatarResult: profileStepResults.isCreatedAvatar avatarResult: profileStepResults.isCreatedAvatar
? 'created' ? 'created'
: profileStepResults.image : profileStepResults.image
? 'uploaded' ? 'uploaded'
: 'default', : 'default',
}) })
})(), })(),
requestNotificationsPermission('AfterOnboarding'), requestNotificationsPermission('AfterOnboarding'),
@@ -214,8 +214,8 @@ let ProfileHeaderLabeler = ({
? t.palette.contrast_50 ? t.palette.contrast_50
: t.palette.contrast_25 : t.palette.contrast_25
: state.hovered || state.pressed : state.hovered || state.pressed
? tokens.color.temp_purple_dark ? tokens.color.temp_purple_dark
: tokens.color.temp_purple, : tokens.color.temp_purple,
}, },
]}> ]}>
<Text <Text
+2 -2
View File
@@ -342,11 +342,11 @@ export function Explore({
]) ])
const topBorder = useMemo( const topBorder = useMemo(
() => ({type: 'topBorder', key: 'top-border'} as const), () => ({type: 'topBorder', key: 'top-border'}) as const,
[], [],
) )
const trendingTopicsModule = useMemo( const trendingTopicsModule = useMemo(
() => ({type: 'trendingTopics', key: 'trending-topics'} as const), () => ({type: 'trendingTopics', key: 'trending-topics'}) as const,
[], [],
) )
const suggestedFollowsModule = useMemo(() => { const suggestedFollowsModule = useMemo(() => {
@@ -2,7 +2,7 @@ import {useMemo} from 'react'
import {msg} from '@lingui/macro' import {msg} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
import {AppIconSet} from '#/screens/Settings/AppIconSettings/types' import {type AppIconSet} from '#/screens/Settings/AppIconSettings/types'
export function useAppIconSets() { export function useAppIconSets() {
const {_} = useLingui() const {_} = useLingui()
@@ -13,20 +13,28 @@ export function useAppIconSets() {
id: 'default_light', id: 'default_light',
name: _(msg({context: 'Name of app icon variant', message: 'Light'})), name: _(msg({context: 'Name of app icon variant', message: 'Light'})),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_default_light.png`) return require(
`../../../../assets/app-icons/ios_icon_default_light.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_default_light.png`) return require(
`../../../../assets/app-icons/android_icon_default_light.png`,
)
}, },
}, },
{ {
id: 'default_dark', id: 'default_dark',
name: _(msg({context: 'Name of app icon variant', message: 'Dark'})), name: _(msg({context: 'Name of app icon variant', message: 'Dark'})),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_default_dark.png`) return require(
`../../../../assets/app-icons/ios_icon_default_dark.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_default_dark.png`) return require(
`../../../../assets/app-icons/android_icon_default_dark.png`,
)
}, },
}, },
] satisfies AppIconSet[] ] satisfies AppIconSet[]
@@ -39,10 +47,14 @@ export function useAppIconSets() {
id: 'core_aurora', id: 'core_aurora',
name: _(msg({context: 'Name of app icon variant', message: 'Aurora'})), name: _(msg({context: 'Name of app icon variant', message: 'Aurora'})),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_aurora.png`) return require(
`../../../../assets/app-icons/ios_icon_core_aurora.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_aurora.png`) return require(
`../../../../assets/app-icons/android_icon_core_aurora.png`,
)
}, },
}, },
// { // {
@@ -59,20 +71,28 @@ export function useAppIconSets() {
id: 'core_sunrise', id: 'core_sunrise',
name: _(msg({context: 'Name of app icon variant', message: 'Sunrise'})), name: _(msg({context: 'Name of app icon variant', message: 'Sunrise'})),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_sunrise.png`) return require(
`../../../../assets/app-icons/ios_icon_core_sunrise.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_sunrise.png`) return require(
`../../../../assets/app-icons/android_icon_core_sunrise.png`,
)
}, },
}, },
{ {
id: 'core_sunset', id: 'core_sunset',
name: _(msg({context: 'Name of app icon variant', message: 'Sunset'})), name: _(msg({context: 'Name of app icon variant', message: 'Sunset'})),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_sunset.png`) return require(
`../../../../assets/app-icons/ios_icon_core_sunset.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_sunset.png`) return require(
`../../../../assets/app-icons/android_icon_core_sunset.png`,
)
}, },
}, },
{ {
@@ -81,10 +101,14 @@ export function useAppIconSets() {
msg({context: 'Name of app icon variant', message: 'Midnight'}), msg({context: 'Name of app icon variant', message: 'Midnight'}),
), ),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_midnight.png`) return require(
`../../../../assets/app-icons/ios_icon_core_midnight.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_midnight.png`) return require(
`../../../../assets/app-icons/android_icon_core_midnight.png`,
)
}, },
}, },
{ {
@@ -93,10 +117,14 @@ export function useAppIconSets() {
msg({context: 'Name of app icon variant', message: 'Flat Blue'}), msg({context: 'Name of app icon variant', message: 'Flat Blue'}),
), ),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_flat_blue.png`) return require(
`../../../../assets/app-icons/ios_icon_core_flat_blue.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_flat_blue.png`) return require(
`../../../../assets/app-icons/android_icon_core_flat_blue.png`,
)
}, },
}, },
{ {
@@ -105,10 +133,14 @@ export function useAppIconSets() {
msg({context: 'Name of app icon variant', message: 'Flat White'}), msg({context: 'Name of app icon variant', message: 'Flat White'}),
), ),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_flat_white.png`) return require(
`../../../../assets/app-icons/ios_icon_core_flat_white.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_flat_white.png`) return require(
`../../../../assets/app-icons/android_icon_core_flat_white.png`,
)
}, },
}, },
{ {
@@ -117,10 +149,14 @@ export function useAppIconSets() {
msg({context: 'Name of app icon variant', message: 'Flat Black'}), msg({context: 'Name of app icon variant', message: 'Flat Black'}),
), ),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_flat_black.png`) return require(
`../../../../assets/app-icons/ios_icon_core_flat_black.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_flat_black.png`) return require(
`../../../../assets/app-icons/android_icon_core_flat_black.png`,
)
}, },
}, },
{ {
@@ -132,10 +168,14 @@ export function useAppIconSets() {
}), }),
), ),
iosImage: () => { iosImage: () => {
return require(`../../../../assets/app-icons/ios_icon_core_classic.png`) return require(
`../../../../assets/app-icons/ios_icon_core_classic.png`,
)
}, },
androidImage: () => { androidImage: () => {
return require(`../../../../assets/app-icons/android_icon_core_classic.png`) return require(
`../../../../assets/app-icons/android_icon_core_classic.png`,
)
}, },
}, },
] satisfies AppIconSet[] ] satisfies AppIconSet[]
@@ -525,8 +525,8 @@ function OwnHandlePage({goToServiceHandle}: {goToServiceHandle: () => void}) {
isVerified isVerified
? _(msg`Update to ${domain}`) ? _(msg`Update to ${domain}`)
: dnsPanel : dnsPanel
? _(msg`Verify DNS Record`) ? _(msg`Verify DNS Record`)
: _(msg`Verify Text File`) : _(msg`Verify Text File`)
} }
variant="solid" variant="solid"
size="large" size="large"
+2 -2
View File
@@ -144,8 +144,8 @@ function mergeShadow<TProfileView extends bsky.profile.AnyProfileView>(
'status' in shadow 'status' in shadow
? shadow.status ? shadow.status
: 'status' in profile : 'status' in profile
? profile.status ? profile.status
: undefined, : undefined,
}) })
} }
+11 -22
View File
@@ -36,38 +36,27 @@ const RQKEY = (feeds: string[]) => [RQKEY_ROOT, feeds]
const LIMIT = 8 // sliced to 6, overfetch to account for moderation const LIMIT = 8 // sliced to 6, overfetch to account for moderation
const PINNED_POST_URIS: Record<string, boolean> = { const PINNED_POST_URIS: Record<string, boolean> = {
// 📰 News // 📰 News
'at://did:plc:kkf4naxqmweop7dv4l2iqqf5/app.bsky.feed.post/3lgh27w2ngc2b': 'at://did:plc:kkf4naxqmweop7dv4l2iqqf5/app.bsky.feed.post/3lgh27w2ngc2b': true,
true,
// Gardening // Gardening
'at://did:plc:5rw2on4i56btlcajojaxwcat/app.bsky.feed.post/3kjorckgcwc27': 'at://did:plc:5rw2on4i56btlcajojaxwcat/app.bsky.feed.post/3kjorckgcwc27': true,
true,
// Web Development Trending // Web Development Trending
'at://did:plc:m2sjv3wncvsasdapla35hzwj/app.bsky.feed.post/3lfaw445axs22': 'at://did:plc:m2sjv3wncvsasdapla35hzwj/app.bsky.feed.post/3lfaw445axs22': true,
true,
// Anime & Manga EN // Anime & Manga EN
'at://did:plc:tazrmeme4dzahimsykusrwrk/app.bsky.feed.post/3knxx2gmkns2y': 'at://did:plc:tazrmeme4dzahimsykusrwrk/app.bsky.feed.post/3knxx2gmkns2y': true,
true,
// 📽️ Film // 📽️ Film
'at://did:plc:2hwwem55ce6djnk6bn62cstr/app.bsky.feed.post/3llhpzhbq7c2g': 'at://did:plc:2hwwem55ce6djnk6bn62cstr/app.bsky.feed.post/3llhpzhbq7c2g': true,
true,
// PopSky // PopSky
'at://did:plc:lfdf4srj43iwdng7jn35tjsp/app.bsky.feed.post/3lbblgly65c2g': 'at://did:plc:lfdf4srj43iwdng7jn35tjsp/app.bsky.feed.post/3lbblgly65c2g': true,
true,
// Science // Science
'at://did:plc:hu2obebw3nhfj667522dahfg/app.bsky.feed.post/3kl33otd6ob2s': 'at://did:plc:hu2obebw3nhfj667522dahfg/app.bsky.feed.post/3kl33otd6ob2s': true,
true,
// Birds! 🦉 // Birds! 🦉
'at://did:plc:ffkgesg3jsv2j7aagkzrtcvt/app.bsky.feed.post/3lbg4r57yk22d': 'at://did:plc:ffkgesg3jsv2j7aagkzrtcvt/app.bsky.feed.post/3lbg4r57yk22d': true,
true,
// Astronomy // Astronomy
'at://did:plc:xy2zorw2ys47poflotxthlzg/app.bsky.feed.post/3kyzye4lujs2w': 'at://did:plc:xy2zorw2ys47poflotxthlzg/app.bsky.feed.post/3kyzye4lujs2w': true,
true,
// What's Cooking 🍽️ // What's Cooking 🍽️
'at://did:plc:geoqe3qls5mwezckxxsewys2/app.bsky.feed.post/3lfqhgvxbqc2q': 'at://did:plc:geoqe3qls5mwezckxxsewys2/app.bsky.feed.post/3lfqhgvxbqc2q': true,
true,
// BookSky 💙📚 #booksky // BookSky 💙📚 #booksky
'at://did:plc:geoqe3qls5mwezckxxsewys2/app.bsky.feed.post/3kgrm2rw5ww2e': 'at://did:plc:geoqe3qls5mwezckxxsewys2/app.bsky.feed.post/3kgrm2rw5ww2e': true,
true,
} }
export type FeedPreviewItem = export type FeedPreviewItem =
+2 -3
View File
@@ -36,9 +36,8 @@ export function useNotificationSettingsUpdateMutation() {
mutationFn: async ( mutationFn: async (
update: Partial<AppBskyNotificationDefs.Preferences>, update: Partial<AppBskyNotificationDefs.Preferences>,
) => { ) => {
const response = await agent.app.bsky.notification.putPreferencesV2( const response =
update, await agent.app.bsky.notification.putPreferencesV2(update)
)
return response.data.preferences return response.data.preferences
}, },
onMutate: update => { onMutate: update => {
+5 -5
View File
@@ -14,7 +14,7 @@ import {useAgent, useSession} from '#/state/session'
import {useModerationOpts} from '../../preferences/moderation-opts' import {useModerationOpts} from '../../preferences/moderation-opts'
import {truncateAndInvalidate} from '../util' import {truncateAndInvalidate} from '../util'
import {RQKEY as RQKEY_NOTIFS} from './feed' import {RQKEY as RQKEY_NOTIFS} from './feed'
import {CachedFeedPage, FeedPage} from './types' import {type CachedFeedPage, type FeedPage} from './types'
import {fetchPage} from './util' import {fetchPage} from './util'
const UPDATE_INTERVAL = 30 * 1e3 // 30sec const UPDATE_INTERVAL = 30 * 1e3 // 30sec
@@ -94,8 +94,8 @@ export function Provider({children}: React.PropsWithChildren<{}>) {
data.event === '30+' data.event === '30+'
? 30 ? 30
: data.event === '' : data.event === ''
? 0 ? 0
: parseInt(data.event, 10) || 1, : parseInt(data.event, 10) || 1,
} }
setNumUnread(data.event) setNumUnread(data.event)
} }
@@ -164,8 +164,8 @@ export function Provider({children}: React.PropsWithChildren<{}>) {
unreadCount >= 30 unreadCount >= 30
? '30+' ? '30+'
: unreadCount === 0 : unreadCount === 0
? '' ? ''
: String(unreadCount) : String(unreadCount)
// track last sync // track last sync
const now = new Date() const now = new Date()
+2 -2
View File
@@ -52,8 +52,8 @@ export function usePostThread({anchor}: {anchor?: string}) {
return view === 'linear' return view === 'linear'
? LINEAR_VIEW_BELOW ? LINEAR_VIEW_BELOW
: isWeb && gtPhone : isWeb && gtPhone
? TREE_VIEW_BELOW_DESKTOP ? TREE_VIEW_BELOW_DESKTOP
: TREE_VIEW_BELOW : TREE_VIEW_BELOW
}, [view, gtPhone]) }, [view, gtPhone])
const postThreadQueryKey = createPostThreadQueryKey({ const postThreadQueryKey = createPostThreadQueryKey({
+1 -1
View File
@@ -444,7 +444,7 @@ export function buildThread({
const anchorPost = items.at(0) const anchorPost = items.at(0)
const hasAnchorFromCache = anchorPost && anchorPost.type === 'threadPost' const hasAnchorFromCache = anchorPost && anchorPost.type === 'threadPost'
const skeletonReplies = hasAnchorFromCache const skeletonReplies = hasAnchorFromCache
? anchorPost.value.post.replyCount ?? 4 ? (anchorPost.value.post.replyCount ?? 4)
: 4 : 4
if (!items.length) { if (!items.length) {
+5 -13
View File
@@ -1,7 +1,7 @@
import {useCallback, useEffect, useState} from 'react' import {useCallback, useEffect, useState} from 'react'
import {MMKV} from 'react-native-mmkv' import {MMKV} from 'react-native-mmkv'
import {Account, Device} from '#/storage/schema' import {type Account, type Device} from '#/storage/schema'
export * from '#/storage/schema' export * from '#/storage/schema'
@@ -83,18 +83,10 @@ export class Storage<Scopes extends unknown[], Schema> {
} }
} }
type StorageSchema<T extends Storage<any, any>> = T extends Storage< type StorageSchema<T extends Storage<any, any>> =
any, T extends Storage<any, infer U> ? U : never
infer U type StorageScopes<T extends Storage<any, any>> =
> T extends Storage<infer S, any> ? S : never
? U
: never
type StorageScopes<T extends Storage<any, any>> = T extends Storage<
infer S,
any
>
? S
: never
/** /**
* Hook to use a storage instance. Acts like a useState hook, but persists the * Hook to use a storage instance. Acts like a useState hook, but persists the
+2 -1
View File
@@ -328,7 +328,8 @@ input[type='range'][orient='vertical']::-moz-range-thumb {
/* #/components/Select/index.web.tsx */ /* #/components/Select/index.web.tsx */
.radix-select-content { .radix-select-content {
box-shadow: 0px 6px 24px -10px rgba(22, 23, 24, 0.25), box-shadow:
0px 6px 24px -10px rgba(22, 23, 24, 0.25),
0px 6px 12px -12px rgba(22, 23, 24, 0.15); 0px 6px 12px -12px rgba(22, 23, 24, 0.15);
min-width: var(--radix-select-trigger-width); min-width: var(--radix-select-trigger-width);
max-height: var(--radix-select-content-available-height); max-height: var(--radix-select-content-available-height);
+16 -16
View File
@@ -518,8 +518,8 @@ export const ComposePost = ({
thread.posts.length > 1 thread.posts.length > 1
? _(msg`Your posts have been published`) ? _(msg`Your posts have been published`)
: replyTo : replyTo
? _(msg`Your reply has been published`) ? _(msg`Your reply has been published`)
: _(msg`Your post has been published`), : _(msg`Your post has been published`),
) )
}, [ }, [
_, _,
@@ -1000,20 +1000,20 @@ function ComposerTopBar({
}), }),
) )
: isThread : isThread
? _( ? _(
msg({ msg({
message: 'Publish posts', message: 'Publish posts',
comment: comment:
'Accessibility label for button to publish multiple posts in a thread', 'Accessibility label for button to publish multiple posts in a thread',
}), }),
) )
: _( : _(
msg({ msg({
message: 'Publish post', message: 'Publish post',
comment: comment:
'Accessibility label for button to publish a single post', 'Accessibility label for button to publish a single post',
}), }),
) )
} }
variant="solid" variant="solid"
color="primary" color="primary"
+10 -10
View File
@@ -1,12 +1,12 @@
import React from 'react' import React from 'react'
import { import {
ImageStyle, type ImageStyle,
Keyboard, Keyboard,
LayoutChangeEvent, type LayoutChangeEvent,
StyleSheet, StyleSheet,
TouchableOpacity, TouchableOpacity,
View, View,
ViewStyle, type ViewStyle,
} from 'react-native' } from 'react-native'
import {Image} from 'expo-image' import {Image} from 'expo-image'
import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome' import {FontAwesomeIcon} from '@fortawesome/react-native-fontawesome'
@@ -14,14 +14,14 @@ import {msg, Trans} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries' import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries'
import {Dimensions} from '#/lib/media/types' import {type Dimensions} from '#/lib/media/types'
import {colors, s} from '#/lib/styles' import {colors, s} from '#/lib/styles'
import {isNative} from '#/platform/detection' import {isNative} from '#/platform/detection'
import {ComposerImage, cropImage} from '#/state/gallery' import {type ComposerImage, cropImage} from '#/state/gallery'
import {Text} from '#/view/com/util/text/Text' import {Text} from '#/view/com/util/text/Text'
import {useTheme} from '#/alf' import {useTheme} from '#/alf'
import * as Dialog from '#/components/Dialog' import * as Dialog from '#/components/Dialog'
import {PostAction} from '../state/composer' import {type PostAction} from '../state/composer'
import {EditImageDialog} from './EditImageDialog' import {EditImageDialog} from './EditImageDialog'
import {ImageAltTextDialog} from './ImageAltTextDialog' import {ImageAltTextDialog} from './ImageAltTextDialog'
@@ -74,8 +74,8 @@ const GalleryInner = ({images, containerInfo, dispatch}: GalleryInnerProps) => {
altTextControlStyle: isOverflow altTextControlStyle: isOverflow
? {left: 4, bottom: 4} ? {left: 4, bottom: 4}
: !isMobile && images.length < 3 : !isMobile && images.length < 3
? {left: 8, top: 8} ? {left: 8, top: 8}
: {left: 4, top: 4}, : {left: 4, top: 4},
imageControlsStyle: { imageControlsStyle: {
display: 'flex' as const, display: 'flex' as const,
flexDirection: 'row' as const, flexDirection: 'row' as const,
@@ -83,8 +83,8 @@ const GalleryInner = ({images, containerInfo, dispatch}: GalleryInnerProps) => {
...(isOverflow ...(isOverflow
? {top: 4, right: 4, gap: 4} ? {top: 4, right: 4, gap: 4}
: !isMobile && images.length < 3 : !isMobile && images.length < 3
? {top: 8, right: 8, gap: 8} ? {top: 8, right: 8, gap: 8}
: {top: 4, right: 4, gap: 4}), : {top: 4, right: 4, gap: 4}),
zIndex: 1, zIndex: 1,
}, },
imageStyle: { imageStyle: {
+21 -16
View File
@@ -1,13 +1,13 @@
import {ImagePickerAsset} from 'expo-image-picker' import {type ImagePickerAsset} from 'expo-image-picker'
import { import {
AppBskyFeedPostgate, type AppBskyFeedPostgate,
AppBskyRichtextFacet, AppBskyRichtextFacet,
BskyPreferences, type BskyPreferences,
RichText, RichText,
} from '@atproto/api' } from '@atproto/api'
import {nanoid} from 'nanoid/non-secure' import {nanoid} from 'nanoid/non-secure'
import {SelfLabel} from '#/lib/moderation' import {type SelfLabel} from '#/lib/moderation'
import {insertMentionAt} from '#/lib/strings/mention-manip' import {insertMentionAt} from '#/lib/strings/mention-manip'
import {shortenLinks} from '#/lib/strings/rich-text-manip' import {shortenLinks} from '#/lib/strings/rich-text-manip'
import { import {
@@ -15,17 +15,22 @@ import {
postUriToRelativePath, postUriToRelativePath,
toBskyAppUrl, toBskyAppUrl,
} from '#/lib/strings/url-helpers' } from '#/lib/strings/url-helpers'
import {ComposerImage, createInitialImages} from '#/state/gallery' import {type ComposerImage, createInitialImages} from '#/state/gallery'
import {createPostgateRecord} from '#/state/queries/postgate/util' import {createPostgateRecord} from '#/state/queries/postgate/util'
import {Gif} from '#/state/queries/tenor' import {type Gif} from '#/state/queries/tenor'
import {threadgateRecordToAllowUISetting} from '#/state/queries/threadgate' import {threadgateRecordToAllowUISetting} from '#/state/queries/threadgate'
import {ThreadgateAllowUISetting} from '#/state/queries/threadgate' import {type ThreadgateAllowUISetting} from '#/state/queries/threadgate'
import {ComposerOpts} from '#/state/shell/composer' import {type ComposerOpts} from '#/state/shell/composer'
import { import {
LinkFacetMatch, type LinkFacetMatch,
suggestLinkCardUri, suggestLinkCardUri,
} from '#/view/com/composer/text-input/text-input-util' } from '#/view/com/composer/text-input/text-input-util'
import {createVideoState, VideoAction, videoReducer, VideoState} from './video' import {
createVideoState,
type VideoAction,
videoReducer,
type VideoState,
} from './video'
type ImagesMedia = { type ImagesMedia = {
type: 'images' type: 'images'
@@ -514,12 +519,12 @@ export function createComposerState({
text: initText text: initText
? initText ? initText
: initMention : initMention
? insertMentionAt( ? insertMentionAt(
`@${initMention}`, `@${initMention}`,
initMention.length + 1, initMention.length + 1,
`${initMention}`, `${initMention}`,
) )
: '', : '',
}) })
let link: Link | undefined let link: Link | undefined
@@ -209,8 +209,8 @@ function AutocompleteProfileCard({
itemIndex === 0 itemIndex === 0
? styles.firstMention ? styles.firstMention
: itemIndex === totalItems - 1 : itemIndex === totalItems - 1
? styles.lastMention ? styles.lastMention
: undefined, : undefined,
]} ]}
onPress={onPress} onPress={onPress}
accessibilityRole="button"> accessibilityRole="button">
+6 -6
View File
@@ -1,17 +1,17 @@
import React, {useCallback, useEffect, useState} from 'react' import React, {useCallback, useEffect, useState} from 'react'
import { import {
Image, Image,
ImageStyle, type ImageStyle,
Pressable, Pressable,
StyleSheet, StyleSheet,
TouchableOpacity, TouchableOpacity,
TouchableWithoutFeedback, TouchableWithoutFeedback,
View, View,
ViewStyle, type ViewStyle,
} from 'react-native' } from 'react-native'
import { import {
FontAwesomeIcon, FontAwesomeIcon,
FontAwesomeIconStyle, type FontAwesomeIconStyle,
} from '@fortawesome/react-native-fontawesome' } from '@fortawesome/react-native-fontawesome'
import {msg} from '@lingui/macro' import {msg} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
@@ -21,7 +21,7 @@ import {useWebMediaQueries} from '#/lib/hooks/useWebMediaQueries'
import {colors, s} from '#/lib/styles' import {colors, s} from '#/lib/styles'
import {useLightbox, useLightboxControls} from '#/state/lightbox' import {useLightbox, useLightboxControls} from '#/state/lightbox'
import {Text} from '../util/text/Text' import {Text} from '../util/text/Text'
import {ImageSource} from './ImageViewing/@types' import {type ImageSource} from './ImageViewing/@types'
import ImageDefaultHeader from './ImageViewing/components/ImageDefaultHeader' import ImageDefaultHeader from './ImageViewing/components/ImageDefaultHeader'
export function Lightbox() { export function Lightbox() {
@@ -121,8 +121,8 @@ function LightboxInner({
img.type === 'circle-avi' img.type === 'circle-avi'
? '50%' ? '50%'
: img.type === 'rect-avi' : img.type === 'rect-avi'
? '10%' ? '10%'
: 0, : 0,
} as ImageStyle } as ImageStyle
} }
alt={img.alt} alt={img.alt}
+2 -2
View File
@@ -630,8 +630,8 @@ let PostThreadItemLoaded = ({
showChildReplyLine && !isThreadedChild showChildReplyLine && !isThreadedChild
? 0 ? 0
: isThreadedChildAdjacentBot : isThreadedChildAdjacentBot
? 4 ? 4
: 8, : 8,
}, },
]}> ]}>
{/* If we are in threaded mode, the avatar is rendered in PostMeta */} {/* If we are in threaded mode, the avatar is rendered in PostMeta */}
+5 -6
View File
@@ -132,12 +132,11 @@ type FeedRow =
key: string key: string
} }
export function getItemsForFeedback(feedRow: FeedRow): export function getItemsForFeedback(feedRow: FeedRow): {
| { item: FeedPostSliceItem
item: FeedPostSliceItem feedContext: string | undefined
feedContext: string | undefined reqId: string | undefined
reqId: string | undefined }[] {
}[] {
if (feedRow.type === 'sliceItem') { if (feedRow.type === 'sliceItem') {
return feedRow.slice.items.map(item => ({ return feedRow.slice.items.map(item => ({
item, item,
+8 -4
View File
@@ -1,15 +1,19 @@
import React from 'react' import React from 'react'
import {View} from 'react-native' import {View} from 'react-native'
import {AppBskyActorDefs, AppBskyFeedGetAuthorFeed, AtUri} from '@atproto/api' import {
type AppBskyActorDefs,
AppBskyFeedGetAuthorFeed,
AtUri,
} from '@atproto/api'
import {msg as msgLingui, Trans} from '@lingui/macro' import {msg as msgLingui, Trans} from '@lingui/macro'
import {useLingui} from '@lingui/react' import {useLingui} from '@lingui/react'
import {useNavigation} from '@react-navigation/native' import {useNavigation} from '@react-navigation/native'
import {usePalette} from '#/lib/hooks/usePalette' import {usePalette} from '#/lib/hooks/usePalette'
import {NavigationProp} from '#/lib/routes/types' import {type NavigationProp} from '#/lib/routes/types'
import {cleanError} from '#/lib/strings/errors' import {cleanError} from '#/lib/strings/errors'
import {logger} from '#/logger' import {logger} from '#/logger'
import {FeedDescriptor} from '#/state/queries/post-feed' import {type FeedDescriptor} from '#/state/queries/post-feed'
import {useRemoveFeedMutation} from '#/state/queries/preferences' import {useRemoveFeedMutation} from '#/state/queries/preferences'
import * as Prompt from '#/components/Prompt' import * as Prompt from '#/components/Prompt'
import {EmptyState} from '../util/EmptyState' import {EmptyState} from '../util/EmptyState'
@@ -119,7 +123,7 @@ function FeedgenErrorMessage({
[KnownError.FeedTooManyRequests]: _l( [KnownError.FeedTooManyRequests]: _l(
msgLingui`This feed is currently receiving high traffic and is temporarily unavailable. Please try again later.`, msgLingui`This feed is currently receiving high traffic and is temporarily unavailable. Please try again later.`,
), ),
}[knownError]), })[knownError],
[_l, knownError], [_l, knownError],
) )
const [_, uri] = feedDesc.split('|') const [_, uri] = feedDesc.split('|')
+6 -6
View File
@@ -461,12 +461,12 @@ let ProfileMenu = ({
msg`The account will be able to interact with you after unblocking.`, msg`The account will be able to interact with you after unblocking.`,
) )
: profile.associated?.labeler : profile.associated?.labeler
? _( ? _(
msg`Blocking will not prevent labels from being applied on your account, but it will stop this account from replying in your threads or interacting with you.`, msg`Blocking will not prevent labels from being applied on your account, but it will stop this account from replying in your threads or interacting with you.`,
) )
: _( : _(
msg`Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you.`, msg`Blocked accounts cannot reply in your threads, mention you, or otherwise interact with you.`,
) )
} }
onConfirm={blockAccount} onConfirm={blockAccount}
confirmButtonCta={ confirmButtonCta={
+8 -3
View File
@@ -1,6 +1,11 @@
import React, {isValidElement, memo, startTransition, useRef} from 'react' import React, {isValidElement, memo, startTransition, useRef} from 'react'
import {FlatListProps, StyleSheet, View, ViewProps} from 'react-native' import {
import {ReanimatedScrollEvent} from 'react-native-reanimated/lib/typescript/hook/commonTypes' type FlatListProps,
StyleSheet,
View,
type ViewProps,
} from 'react-native'
import {type ReanimatedScrollEvent} from 'react-native-reanimated/lib/typescript/hook/commonTypes'
import {batchedUpdates} from '#/lib/batchedUpdates' import {batchedUpdates} from '#/lib/batchedUpdates'
import {useNonReactiveCallback} from '#/lib/hooks/useNonReactiveCallback' import {useNonReactiveCallback} from '#/lib/hooks/useNonReactiveCallback'
@@ -205,7 +210,7 @@ function ListImpl<ItemT>(
behavior: animated ? 'smooth' : 'instant', behavior: animated ? 'smooth' : 'instant',
}) })
}, },
} as any), // TODO: Better types. }) as any, // TODO: Better types.
[getScrollableNode], [getScrollableNode],
) )
+8 -8
View File
@@ -112,14 +112,14 @@ export const DebugModScreen = ({}: NativeStackScreenProps<
}), }),
] ]
: scenario[0] === 'label' && target[0] === 'profile' : scenario[0] === 'label' && target[0] === 'profile'
? [ ? [
mock.label({ mock.label({
src: isSelfLabel ? did : undefined, src: isSelfLabel ? did : undefined,
val: label[0], val: label[0],
uri: `at://${did}/app.bsky.actor.profile/self`, uri: `at://${did}/app.bsky.actor.profile/self`,
}), }),
] ]
: undefined, : undefined,
viewer: mock.actorViewerState({ viewer: mock.actorViewerState({
following: isFollowing following: isFollowing
? `at://${currentAccount?.did || ''}/app.bsky.graph.follow/1234` ? `at://${currentAccount?.did || ''}/app.bsky.graph.follow/1234`
+61 -59
View File
@@ -1,64 +1,66 @@
const preset = [ const preset = [
"removeDoctype", 'removeDoctype',
"removeXMLProcInst", 'removeXMLProcInst',
"removeComments", 'removeComments',
"removeMetadata", 'removeMetadata',
"removeEditorsNSData", 'removeEditorsNSData',
"cleanupAttrs", 'cleanupAttrs',
"mergeStyles", 'mergeStyles',
"inlineStyles", 'inlineStyles',
"minifyStyles", 'minifyStyles',
"cleanupIds", 'cleanupIds',
"removeUselessDefs", 'removeUselessDefs',
"cleanupNumericValues", 'cleanupNumericValues',
"convertColors", 'convertColors',
"removeUnknownsAndDefaults", 'removeUnknownsAndDefaults',
"removeNonInheritableGroupAttrs", 'removeNonInheritableGroupAttrs',
"removeUselessStrokeAndFill", 'removeUselessStrokeAndFill',
"removeDimensions", 'removeDimensions',
"cleanupEnableBackground", 'cleanupEnableBackground',
"removeHiddenElems", 'removeHiddenElems',
"removeEmptyText", 'removeEmptyText',
"convertShapeToPath", 'convertShapeToPath',
"convertEllipseToCircle", 'convertEllipseToCircle',
"moveElemsAttrsToGroup", 'moveElemsAttrsToGroup',
"moveGroupAttrsToElems", 'moveGroupAttrsToElems',
"collapseGroups", 'collapseGroups',
"convertPathData", 'convertPathData',
"convertTransform", 'convertTransform',
"removeEmptyAttrs", 'removeEmptyAttrs',
"removeEmptyContainers", 'removeEmptyContainers',
"removeUnusedNS", 'removeUnusedNS',
"mergePaths", 'mergePaths',
"sortAttrs", 'sortAttrs',
"sortDefsChildren", 'sortDefsChildren',
"removeTitle", 'removeTitle',
"removeDesc", 'removeDesc',
] ]
export default { export default {
plugins: [...preset.map(name => ({ plugins: [
name, ...preset.map(name => ({
params: { name,
floatPrecision: 3, params: {
transformPrecision: 5, floatPrecision: 3,
// minimise diff in ouput from svgomg transformPrecision: 5,
// maybe remove in future? will produce smaller output // minimise diff in ouput from svgomg
convertToZ: false, // maybe remove in future? will produce smaller output
removeUseless: false, convertToZ: false,
} removeUseless: false,
})), },
{ })),
name: 'addTrailingWhitespace', {
fn() { name: 'addTrailingWhitespace',
return { fn() {
root: { return {
exit (root) { root: {
root.children.push({ type: 'text', value: '\n' }) exit(root) {
return root root.children.push({type: 'text', value: '\n'})
} return root
},
},
} }
} },
} },
}] ],
}; }
+4 -4
View File
@@ -16220,10 +16220,10 @@ prelude-ls@^1.2.1:
resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396" resolved "https://registry.yarnpkg.com/prelude-ls/-/prelude-ls-1.2.1.tgz#debc6489d7a6e6b0e7611888cec880337d316396"
integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g== integrity sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==
prettier@^2.8.3: prettier@^3.6.0:
version "2.8.8" version "3.6.0"
resolved "https://registry.yarnpkg.com/prettier/-/prettier-2.8.8.tgz#e8c5d7e98a4305ffe3de2e1fc4aca1a71c28b1da" resolved "https://registry.yarnpkg.com/prettier/-/prettier-3.6.0.tgz#18ec98d62cb0757a5d4eab40253ff3e6d0fc8dea"
integrity sha512-tdN8qQGvNjw4CHbY+XXk0JgCXn9QiF21a55rBe5LJAU+kDyC4WQn4+awm2Xfk2lQMk5fKup9XgzTZtGkjBdP9Q== integrity sha512-ujSB9uXHJKzM/2GBuE0hBOUgC77CN3Bnpqa+g80bkv3T3A93wL/xlzDATHhnhkzifz/UE2SNOvmbTz5hSkDlHw==
pretty-bytes@^5.6.0: pretty-bytes@^5.6.0:
version "5.6.0" version "5.6.0"