Include short bios by default and fill those no-bio cards with work and interests

This commit is contained in:
MartinBraquet
2026-01-28 22:58:44 +01:00
parent a433d1e095
commit b01dcc6bde
5 changed files with 62 additions and 30 deletions

View File

@@ -104,16 +104,16 @@ export const loadProfiles = async (props: profileQueryType) => {
const userActivityJoin = 'user_activity on user_activity.user_id = profiles.user_id'
const joinInterests = !!interests?.length
const joinInterests = true // !!interests?.length
const joinCauses = !!causes?.length
const joinWork = !!work?.length
const joinWork = true // !!work?.length
// Pre-aggregated interests per profile
function getManyToManyJoin(label: OptionTableKey) {
return `(
SELECT
profile_${label}.profile_id,
ARRAY_AGG(${label}.name ORDER BY ${label}.name) AS ${label}
ARRAY_AGG(${label}.id ORDER BY ${label}.id) AS ${label}
FROM profile_${label}
JOIN ${label} ON ${label}.id = profile_${label}.option_id
GROUP BY profile_${label}.profile_id

View File

@@ -86,7 +86,7 @@ export const initialFilters: Partial<FilterFields> = {
religion: undefined,
mbti: undefined,
pref_gender: undefined,
shortBio: undefined,
shortBio: true,
drinks_min: undefined,
drinks_max: undefined,
orderBy: 'created_time',

View File

@@ -1,5 +1,5 @@
import clsx from 'clsx'
import {convertRace, convertRelationshipType, type RelationshipType,} from 'web/lib/util/convert-types'
import {convertRace, type RelationshipType,} from 'web/lib/util/convert-types'
import stringOrStringArrayToText from 'web/lib/util/string-or-string-array-to-text'
import React, {ReactNode} from 'react'
import {
@@ -10,7 +10,6 @@ import {
INVERTED_POLITICAL_CHOICES,
INVERTED_RELATIONSHIP_STATUS_CHOICES,
INVERTED_RELIGION_CHOICES,
INVERTED_ROMANTIC_CHOICES,
RELATIONSHIP_ICONS
} from 'web/components/filters/choices'
import {BiSolidDrink} from 'react-icons/bi'
@@ -34,6 +33,7 @@ import {GiFruitBowl} from "react-icons/gi";
import {FaBriefcase, FaHandsHelping, FaHeart, FaStar} from "react-icons/fa";
import {useLocale, useT} from "web/lib/locale";
import {useChoices} from "web/hooks/use-choices";
import {getSeekingGenderText} from "web/lib/profile/seeking";
export function AboutRow(props: {
icon: ReactNode
@@ -188,25 +188,7 @@ function Seeking(props: { profile: Profile }) {
function RelationshipType(props: { profile: Profile }) {
const t = useT()
const {profile} = props
const relationshipTypes = profile.pref_relation_styles
let seekingGenderText = stringOrStringArrayToText({
text: relationshipTypes?.map((rel) =>
t(`profile.relationship.${rel}`, convertRelationshipType(rel as RelationshipType)).toLowerCase()
).sort(),
preText: t('profile.seeking', 'Seeking'),
asSentence: true,
capitalizeFirstLetterOption: false,
t: t,
})
if (relationshipTypes?.includes('relationship')) {
const romanticStyles = profile.pref_romantic_styles
?.map((style) => t(`profile.romantic.${style}`, INVERTED_ROMANTIC_CHOICES[style]).toLowerCase())
.filter(Boolean)
if (romanticStyles && romanticStyles.length > 0) {
seekingGenderText += ` (${romanticStyles.join(', ')})`
}
}
const seekingGenderText = getSeekingGenderText(profile, t)
return (
<AboutRow
icon={<BsPersonHeart className="h-5 w-5"/>}

View File

@@ -12,6 +12,8 @@ import {Row} from "web/components/layout/row";
import {CompatibleBadge} from "web/components/widgets/compatible-badge";
import {useUser} from "web/hooks/use-user";
import {useT} from "web/lib/locale";
import {useAllChoices} from "web/hooks/use-choices";
import {getSeekingGenderText} from "web/lib/profile/seeking";
export const ProfileGrid = (props: {
profiles: Profile[]
@@ -83,6 +85,8 @@ function ProfilePreview(props: {
}) {
const {profile, compatibilityScore} = props
const {user} = profile
const choicesIdsToLabels = useAllChoices()
const t = useT()
// const currentUser = useUser()
const bio = profile.bio as JSONContent;
@@ -110,6 +114,12 @@ function ProfilePreview(props: {
bio.content = newBio
}
const seekingGenderText = getSeekingGenderText(profile, t)
if (!profile.work?.length && !profile.occupation_title && !profile.interests?.length && (profile.bio_length || 0) < 100) {
return null
}
return (
<Link
onClick={() => track('click profile preview')}
@@ -152,18 +162,31 @@ function ProfilePreview(props: {
)}
</Row>
<Col className="absolute inset-x-0 bottom-0 bg-gradient-to-t to-transparent px-4 pb-2 pt-6">
<Col className="absolute inset-x-0 top-[-15px] bg-gradient-to-b to-transparent px-4 pt-0">
<div>
<div className="flex-1 min-w-0">
{/* <OnlineIcon last_online_time={last_online_time} /> */}
<h3 className="text-lg font-medium text-gray-900 dark:text-white truncate">
{user.name}
{user.name}{profile.age && `, ${profile.age}`}
{/*{profile.gender && <GenderIcon gender={profile.gender} className={clsx('h-4 w-4')} hasColor />}*/}
</h3>
<div className="text-sm text-gray-500 dark:text-gray-400">
<div className="line-clamp-4">
{/*TODO: fix nested <a> links warning (one from Link above, one from link in bio below)*/}
<Content className="w-full line-clamp-4" content={bio}/>
<Content className="w-full" content={bio}/>
{/*<Col>*/}
{seekingGenderText && <p>{seekingGenderText}.</p>}
{!!profile.work?.length && <p>
{t("profile.optional.category.work", "Work")}:{" "}
{profile.occupation_title && profile.occupation_title + ", "}
{profile.work?.slice(0, 3).map(id => choicesIdsToLabels['work'][id]).join(', ')}
{(profile.work?.length || 0) > 3 && ',...'}
</p>}
{!!profile.interests?.length && <p>
{t("profile.optional.interests", "Interests")}:{" "}
{profile.interests?.map(id => choicesIdsToLabels['interests'][id]).join(', ')}
</p>}
{/*</Col>*/}
</div>
{/*{age}*/}
</div>
</div>
{/*<Row className="gap-1 text-xs">*/}

View File

@@ -0,0 +1,27 @@
import {convertRelationshipType, RelationshipType} from "web/lib/util/convert-types";
import stringOrStringArrayToText from "web/lib/util/string-or-string-array-to-text";
import {Profile} from "common/profiles/profile";
import {INVERTED_ROMANTIC_CHOICES} from "web/components/filters/choices";
export function getSeekingGenderText(profile: Profile, t: any) {
const relationshipTypes = profile.pref_relation_styles
if (!relationshipTypes?.length) return ''
let seekingGenderText = stringOrStringArrayToText({
text: relationshipTypes?.map((rel) =>
t(`profile.relationship.${rel}`, convertRelationshipType(rel as RelationshipType)).toLowerCase()
).sort(),
preText: t('profile.seeking', 'Seeking'),
asSentence: true,
capitalizeFirstLetterOption: false,
t: t,
})
if (relationshipTypes?.includes('relationship')) {
const romanticStyles = profile.pref_romantic_styles
?.map((style) => t(`profile.romantic.${style}`, INVERTED_ROMANTIC_CHOICES[style]).toLowerCase())
.filter(Boolean)
if (romanticStyles && romanticStyles.length > 0) {
seekingGenderText += ` (${romanticStyles.join(', ')})`
}
}
return seekingGenderText
}