h
h
TtRPC
Created by h on 12/3/2023 in #❓-help
Comparing tRPC and Server Actions for a SaaS Template: Seeking Insights and Advice
Hey everyone πŸ‘‹, I've just posted a detailed comparison and discussion request on Reddit about tRPC vs. Server Actions in the context of a SaaS template using Next.js. My current setup uses tRPC with its experimental feature for server actions, and I'm considering a switch due to the community's lean towards server actions. Main points I'm pondering: - The abstraction and built-in features like caching in tRPC. - The need for custom implementation of these features in server actions. - The suitability of either approach for a unified API across web and mobile (React Native future plans). I'm at a crossroads and could really use your insights, especially if you've tackled similar challenges. Check out the full post and let's discuss: Reddit Post Looking forward to your thoughts and advice!
3 replies
TtRPC
Created by h on 10/8/2023 in #❓-help
Auth through trpc procedures
Has Anyone Successfully Implemented Supabase Auth through tRPC Procedures in a Next.js App? Hello everyone πŸ‘‹, I'm currently working on a Next.js project and trying to handle authentication using Supabase and tRPC. While I've been able to perform authentication directly via the Supabase client, I'm running into some issues when attempting to do the same through tRPC procedures. Specifically, sessions are not being added to cookies. Here's a snippet of my tRPC auth service routes:
export const authServiceRoutes = router({
signup: publicProcedure
.input(SignupInput)
.mutation(async ({ ctx: { supabase }, input: { email, password } }) => {
// Signup Logic
}),
login: publicProcedure
.input(LoginInput)
.mutation(async ({ ctx: { supabase }, input: { email, password } }) => {
// Login Logic
})
})
export const authServiceRoutes = router({
signup: publicProcedure
.input(SignupInput)
.mutation(async ({ ctx: { supabase }, input: { email, password } }) => {
// Signup Logic
}),
login: publicProcedure
.input(LoginInput)
.mutation(async ({ ctx: { supabase }, input: { email, password } }) => {
// Login Logic
})
})
When I perform authentication directly using Supabase like so:
await supabase.auth.signInWithPassword({ email, password });
await supabase.auth.signInWithPassword({ email, password });
Everything works as expected. However, using my tRPC procedures doesn't seem to set the session in the cookies. Has anyone faced a similar issue or successfully implemented this kind of setup? Any help would be much appreciated
10 replies
TtRPC
Created by h on 10/8/2023 in #❓-help
supabase + trpc
did anyone handle to make it work -> context and all signup signin etc methods?
2 replies
TtRPC
Created by h on 9/12/2023 in #❓-help
how to handle error from Zod in trpc?
I would like to return error instead throwing it away so i could show user nice feedback i found https://zod.dev/?id=safeparse but i dont know how to implement it
signup: authProcedure
.input(SignupInput)
.mutation(
async ({
ctx: { supabase },
input: { email, password, repeatPassword },
}) => {
const user = await supabase.auth.getSession()
console.log(user.data.session)
console.log(email, password, repeatPassword)
}
),


export const SignupInput = z
.object({
password: z.string().min(8),
repeatPassword: z.string().min(8),
})
.refine(data => data.password === data.repeatPassword, {
message: "Passwords don't match",
path: ['repeatPassword'],
})
signup: authProcedure
.input(SignupInput)
.mutation(
async ({
ctx: { supabase },
input: { email, password, repeatPassword },
}) => {
const user = await supabase.auth.getSession()
console.log(user.data.session)
console.log(email, password, repeatPassword)
}
),


export const SignupInput = z
.object({
password: z.string().min(8),
repeatPassword: z.string().min(8),
})
.refine(data => data.password === data.repeatPassword, {
message: "Passwords don't match",
path: ['repeatPassword'],
})
4 replies
TtRPC
Created by h on 9/11/2023 in #❓-help
Which one method should I use for creating trpc for server componetns in Nextjs 13 App dir
Hi which one I should use experimental_createTRPCNextAppDirServer or createTRPCProxyClient when it comes to defining trpc api for the server components? I mean both works fine with next13 app dir and im confused
3 replies
TtRPC
Created by h on 9/5/2023 in #❓-help
wrapper on useMutation (and another for useQuery) for creating multiple hooks
hi i want to create a wrapper for my router, basically I would like to achive somethink like that This is my appRouter:
export const appRouter = router({
todoService: todoServiceRoutes,
})

export type AppRouter = typeof appRouter
export const appRouter = router({
todoService: todoServiceRoutes,
})

export type AppRouter = typeof appRouter
This is my todoService router:
export const todoServiceRoutes = router({
add: publicProcedure
.input(apiTodoSchemaValidator.insertTodoSchema)
.mutation(async ({ input: { title, description, isDone } }) => {
return db
.insert(todos)
.values({
title,
description,
isDone,
})
.returning({ insertedId: todos.id })
}),
getAll: publicProcedure.query(async () => {
return db.select().from(todos).orderBy(desc(todos.id))
})
})
export const todoServiceRoutes = router({
add: publicProcedure
.input(apiTodoSchemaValidator.insertTodoSchema)
.mutation(async ({ input: { title, description, isDone } }) => {
return db
.insert(todos)
.values({
title,
description,
isDone,
})
.returning({ insertedId: todos.id })
}),
getAll: publicProcedure.query(async () => {
return db.select().from(todos).orderBy(desc(todos.id))
})
})
This is my wannabe custom hook:
export function useCustomMutation<T extends AppRouter>(
config: ProcedureConfig<T>
) {
const utils = api.useContext()

const { service, action, optimisticUpdateEndpoint } = config

return api[service][action].useMutation({
onMutate: async input => {
await utils[service][optimisticUpdateEndpoint].cancel()
const updatedResults = utils[service][optimisticUpdateEndpoint].getData()

const optimisticUpdate = updatedResults && [
{ ...input, id: updatedResults.length + 1 },
...updatedResults,
]

utils[service][optimisticUpdateEndpoint].setData(
undefined,
optimisticUpdate
)
},
onError: () => {
utils[service][optimisticUpdateEndpoint].invalidate()
},
onSuccess: () => {
utils[service][optimisticUpdateEndpoint].invalidate()
},
})
}
export function useCustomMutation<T extends AppRouter>(
config: ProcedureConfig<T>
) {
const utils = api.useContext()

const { service, action, optimisticUpdateEndpoint } = config

return api[service][action].useMutation({
onMutate: async input => {
await utils[service][optimisticUpdateEndpoint].cancel()
const updatedResults = utils[service][optimisticUpdateEndpoint].getData()

const optimisticUpdate = updatedResults && [
{ ...input, id: updatedResults.length + 1 },
...updatedResults,
]

utils[service][optimisticUpdateEndpoint].setData(
undefined,
optimisticUpdate
)
},
onError: () => {
utils[service][optimisticUpdateEndpoint].invalidate()
},
onSuccess: () => {
utils[service][optimisticUpdateEndpoint].invalidate()
},
})
}
and thats how I want to use it:
export function useAddTodo() {
const { mutation, isLoading } = useCustomMutation({
service: 'todoService',
action: 'add',
optimisticUpdateEndpoint: 'getAll',
})
export function useAddTodo() {
const { mutation, isLoading } = useCustomMutation({
service: 'todoService',
action: 'add',
optimisticUpdateEndpoint: 'getAll',
})
now how I can make it typesafe with intellisense (code completition, etc)
1 replies
TtRPC
Created by h on 8/31/2023 in #❓-help
re validation on static site next js 13
Hi, does any one know how to make revaluation when I’m fetching data on the server client from DB with usage of trpc react query? import AddTodo from '@/app/(routes)/(account)/todo/_components/AddTodo' import { TodoList } from '@/app/_components' import { serverClient } from '@/app/_utils/api/serverClient' export const metadata = { title: 'Todos', description: 'list of my todos', } export default async function Todos() { const initialTodos = await serverClient.todoService.getAll() return ( <main className='flex min-h-screen flex-col items-center justify-between space-y-8 bg-gray-100 p-12'> <h1 className='text-3xl font-bold'>Todo </h1> <div className='w-full max-w-xl'> <AddTodo /> <TodoList initialTodos={initialTodos} /> </div> </main ) } Right now it’s SSG and I want it to be ISR
2 replies