Skip to content

Commit c1b99c6

Browse files
committed
add landing page features & fix gpt response
1 parent 4e56986 commit c1b99c6

File tree

5 files changed

+72
-38
lines changed

5 files changed

+72
-38
lines changed

app/src/client/app/AccountPage.tsx

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { useState, useEffect } from 'react';
12
import { User } from '@wasp/entities';
23
import { useQuery } from '@wasp/queries';
34
import getGptResponses from '@wasp/queries/getGptResponses';
@@ -7,8 +8,14 @@ import { STRIPE_CUSTOMER_PORTAL_LINK } from '@wasp/shared/constants';
78
import { TierIds } from '@wasp/shared/constants';
89

910
export default function AccountPage({ user }: { user: User }) {
11+
const [ lastGptResponse, setLastGptResponse ] = useState<string[]>([]);
1012
const { data: gptResponses, isLoading: isLoadingGptResponses } = useQuery(getGptResponses);
1113

14+
useEffect(() => {
15+
if (gptResponses && gptResponses.length > 0) {
16+
setLastGptResponse(gptResponses[gptResponses.length - 1].content.split('\n'));
17+
}
18+
}, [gptResponses]);
1219
return (
1320
<div className='mt-10 px-6'>
1421
<div className='overflow-hidden bg-white ring-1 ring-gray-900/10 shadow-lg sm:rounded-lg lg:m-8 '>
@@ -51,11 +58,10 @@ export default function AccountPage({ user }: { user: User }) {
5158
</div>
5259
<div className='py-4 sm:grid sm:grid-cols-3 sm:gap-4 sm:py-5 sm:px-6'>
5360
<dt className='text-sm font-medium text-gray-500'>Most Recent GPT Response</dt>
54-
<dd className='mt-1 text-sm text-gray-900 sm:col-span-2 sm:mt-0'>
61+
<dd className='flex flex-col gap-2 mt-1 text-sm text-gray-900 sm:col-span-2 sm:mt-0'>
5562
{isLoadingGptResponses
5663
? 'Loading...'
57-
: !!gptResponses && gptResponses.length > 0
58-
? gptResponses[gptResponses.length - 1].content
64+
: lastGptResponse.length > 0 ? lastGptResponse.map((str) => <p key={str}>{str}</p>)
5965
: "You don't have any at this time."}
6066
</dd>
6167
</div>

app/src/client/app/GptPage.tsx

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import useAuth from '@wasp/auth/useAuth';
55

66
export default function GptPage() {
77
const [temperature, setTemperature] = useState<number>(1);
8-
const [response, setResponse] = useState<string>('');
8+
const [response, setResponse] = useState<string[]>([]);
99

1010
const { data: user } = useAuth();
1111

@@ -18,11 +18,12 @@ export default function GptPage() {
1818
try {
1919
const response = await generateGptResponse({ instructions, command, temperature });
2020
if (response) {
21-
setResponse(response.content);
21+
setResponse(response.split('\n'));
22+
console.log(response)
2223
}
23-
} catch (e) {
24-
alert('Something went wrong. Please try again.');
25-
console.error(e);
24+
} catch (error: any) {
25+
alert(error.message);
26+
console.error(error);
2627
}
2728
};
2829

@@ -124,7 +125,7 @@ export default function GptPage() {
124125
<button
125126
type='submit'
126127
className={`${
127-
isSubmitting && 'animate-puls'
128+
isSubmitting && 'opacity-70 cursor-wait'
128129
} rounded-md bg-yellow-500 py-2 px-3 text-sm font-semibold text-white shadow-sm hover:bg-yellow-600 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-indigo-600`}
129130
>
130131
{!isSubmitting ? 'Submit' : 'Loading...'}
@@ -134,10 +135,10 @@ export default function GptPage() {
134135
<div
135136
className={`${
136137
isSubmitting && 'animate-pulse'
137-
} mt-2 mx-6 flex justify-center rounded-lg border border-dashed border-gray-900/25 mt-10 sm:w-[90%] md:w-[50%] mx-auto mt-12 px-6 py-10`}
138+
} mt-4 mx-6 flex justify-center rounded-lg border border-dashed border-gray-900/25 sm:w-[90%] md:w-[50%] mx-auto mt-12 px-6 py-10`}
138139
>
139-
<div className='space-y-2 text-center'>
140-
<p className='text-sm text-gray-500'>{response ? response : 'GPT Response will load here'}</p>
140+
<div className='space-y-2 flex flex-col gap-2 text-center text-sm text-gray-500 w-full'>
141+
{response.length > 0 ? response.map((str) => <p key={str}>{str}</p>) : <p>GPT Response will load here</p>}
141142
</div>
142143
</div>
143144
</div>

app/src/client/landing-page/LandingPage.tsx

Lines changed: 41 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -217,15 +217,15 @@ export default function LandingPage() {
217217
<div className='mt-12 mx-auto max-w-7xl px-6 lg:px-8 flex flex-col items-between gap-y-6'>
218218
<h2 className='mb-6 text-center font-semibold tracking-wide text-gray-500'>Built and Ships with</h2>
219219

220-
<div className='mx-auto grid max-w-lg grid-cols-2 items-center gap-x-8 gap-y-12 sm:max-w-xl md:grid-cols-6 sm:gap-x-10 sm:gap-y-14 lg:mx-0 lg:max-w-none'>
220+
<div className='mx-auto grid max-w-lg grid-cols-2 items-center gap-x-8 gap-y-12 sm:max-w-xl md:grid-cols-4 sm:gap-x-10 sm:gap-y-14 lg:mx-0 lg:max-w-none'>
221221
<img
222222
className=' col-span-1 max-h-12 w-full object-contain grayscale opacity-100'
223223
src='https://upload.wikimedia.org/wikipedia/commons/thumb/a/a7/React-icon.svg/512px-React-icon.svg.png'
224224
alt='React'
225225
height={48}
226226
/>
227227
<img
228-
className=' col-span-1 max-h-12 w-full object-contain grayscale opacity-70 '
228+
className=' col-span-1 max-h-12 w-full object-contain grayscale opacity-60 '
229229
src='https://upload.wikimedia.org/wikipedia/commons/thumb/d/d9/Node.js_logo.svg/590px-Node.js_logo.svg.png'
230230
alt='NodeJS'
231231
height={48}
@@ -238,7 +238,6 @@ export default function LandingPage() {
238238
/>
239239
<div className='flex justify-center col-span-1 max-h-12 w-full object-contain grayscale opacity-80'>
240240
<svg width={48} height={48} viewBox='0 0 32 32' xmlns='http://www.w3.org/2000/svg'>
241-
<title>file_type_prisma</title>
242241
<path
243242
fill='#545454'
244243
d='M25.21,24.21,12.739,27.928a.525.525,0,0,1-.667-.606L16.528,5.811a.43.43,0,0,1,.809-.094l8.249,17.661A.6.6,0,0,1,25.21,24.21Zm2.139-.878L17.8,2.883h0A1.531,1.531,0,0,0,16.491,2a1.513,1.513,0,0,0-1.4.729L4.736,19.648a1.592,1.592,0,0,0,.018,1.7l5.064,7.909a1.628,1.628,0,0,0,1.83.678l14.7-4.383a1.6,1.6,0,0,0,1-2.218Z'
@@ -257,6 +256,30 @@ export default function LandingPage() {
257256
alt='Stripe'
258257
height={48}
259258
/>
259+
<div className='flex justify-center col-span-1 w-full max-h-12 object-contain grayscale opacity-75'>
260+
<svg viewBox='0 0 256 370' xmlns='http://www.w3.org/2000/svg'>
261+
<path
262+
fill='#545454'
263+
d='M182.022 9.147c2.982 3.702 4.502 8.697 7.543 18.687L256 246.074a276.467 276.467 0 0 0-79.426-26.891L133.318 73.008a5.63 5.63 0 0 0-10.802.017L79.784 219.11A276.453 276.453 0 0 0 0 246.04L66.76 27.783c3.051-9.972 4.577-14.959 7.559-18.654a24.541 24.541 0 0 1 9.946-7.358C88.67 0 93.885 0 104.314 0h47.683c10.443 0 15.664 0 20.074 1.774a24.545 24.545 0 0 1 9.95 7.373Z'
264+
/>
265+
<path
266+
fill='#545454'
267+
d='M189.972 256.46c-10.952 9.364-32.812 15.751-57.992 15.751-30.904 0-56.807-9.621-63.68-22.56-2.458 7.415-3.009 15.903-3.009 21.324 0 0-1.619 26.623 16.898 45.14 0-9.615 7.795-17.41 17.41-17.41 16.48 0 16.46 14.378 16.446 26.043l-.001 1.041c0 17.705 10.82 32.883 26.21 39.28a35.685 35.685 0 0 1-3.588-15.647c0-16.886 9.913-23.173 21.435-30.48 9.167-5.814 19.353-12.274 26.372-25.232a47.588 47.588 0 0 0 5.742-22.735c0-5.06-.786-9.938-2.243-14.516Z'
268+
/>
269+
</svg>
270+
</div>
271+
<div className='flex justify-center col-span-1 w-full max-h-12 object-contain grayscale opacity-75'>
272+
<svg
273+
xmlns='http://www.w3.org/2000/svg'
274+
preserveAspectRatio='xMidYMid'
275+
viewBox='0 0 256 260'
276+
>
277+
<path
278+
fill='#545454'
279+
d='M239.184 106.203a64.716 64.716 0 0 0-5.576-53.103C219.452 28.459 191 15.784 163.213 21.74A65.586 65.586 0 0 0 52.096 45.22a64.716 64.716 0 0 0-43.23 31.36c-14.31 24.602-11.061 55.634 8.033 76.74a64.665 64.665 0 0 0 5.525 53.102c14.174 24.65 42.644 37.324 70.446 31.36a64.72 64.72 0 0 0 48.754 21.744c28.481.025 53.714-18.361 62.414-45.481a64.767 64.767 0 0 0 43.229-31.36c14.137-24.558 10.875-55.423-8.083-76.483Zm-97.56 136.338a48.397 48.397 0 0 1-31.105-11.255l1.535-.87 51.67-29.825a8.595 8.595 0 0 0 4.247-7.367v-72.85l21.845 12.636c.218.111.37.32.409.563v60.367c-.056 26.818-21.783 48.545-48.601 48.601Zm-104.466-44.61a48.345 48.345 0 0 1-5.781-32.589l1.534.921 51.722 29.826a8.339 8.339 0 0 0 8.441 0l63.181-36.425v25.221a.87.87 0 0 1-.358.665l-52.335 30.184c-23.257 13.398-52.97 5.431-66.404-17.803ZM23.549 85.38a48.499 48.499 0 0 1 25.58-21.333v61.39a8.288 8.288 0 0 0 4.195 7.316l62.874 36.272-21.845 12.636a.819.819 0 0 1-.767 0L41.353 151.53c-23.211-13.454-31.171-43.144-17.804-66.405v.256Zm179.466 41.695-63.08-36.63L161.73 77.86a.819.819 0 0 1 .768 0l52.233 30.184a48.6 48.6 0 0 1-7.316 87.635v-61.391a8.544 8.544 0 0 0-4.4-7.213Zm21.742-32.69-1.535-.922-51.619-30.081a8.39 8.39 0 0 0-8.492 0L99.98 99.808V74.587a.716.716 0 0 1 .307-.665l52.233-30.133a48.652 48.652 0 0 1 72.236 50.391v.205ZM88.061 139.097l-21.845-12.585a.87.87 0 0 1-.41-.614V65.685a48.652 48.652 0 0 1 79.757-37.346l-1.535.87-51.67 29.825a8.595 8.595 0 0 0-4.246 7.367l-.051 72.697Zm11.868-25.58 28.138-16.217 28.188 16.218v32.434l-28.086 16.218-28.188-16.218-.052-32.434Z'
280+
/>
281+
</svg>
282+
</div>
260283
</div>
261284
</div>
262285

@@ -274,8 +297,8 @@ export default function LandingPage() {
274297
</div>
275298
<div className='mx-auto mt-16 max-w-2xl sm:mt-20 lg:mt-24 lg:max-w-4xl'>
276299
<dl className='grid max-w-xl grid-cols-1 gap-x-8 gap-y-10 lg:max-w-none lg:grid-cols-2 lg:gap-y-16'>
277-
{features.map((feature, idx) => (
278-
<div key={feature.name} className={`relative pl-16 ${idx === features.length - 1 ? `mx-auto lg:col-span-2 lg:w-1/2` : ''}`}>
300+
{features.map((feature) => (
301+
<div key={feature.name} className={`relative pl-16`}>
279302
<dt className='text-base font-semibold leading-7 text-gray-900'>
280303
<div className='absolute left-0 top-0 flex h-10 w-10 items-center justify-center border border-yellow-400 bg-yellow-100/50 rounded-lg'>
281304
<div className='text-2xl'>{feature.icon}</div>
@@ -297,24 +320,19 @@ export default function LandingPage() {
297320
<div className='relative flex flex-wrap gap-6 w-full mt-6 z-10 justify-between lg:mx-0'>
298321
{testimonials.map((testimonial) => (
299322
<figure className='w-full lg:w-1/4 box-content flex flex-col justify-between p-8 rounded-xl bg-gray-500/5 '>
300-
<blockquote className='text-lg text-white sm:text-md sm:leading-8'>
301-
<p>
302-
{testimonial.quote}
303-
</p>
304-
</blockquote>
305-
<figcaption className='mt-6 text-base text-white'>
306-
<a href={testimonial.socialUrl} className='flex items-center gap-x-2'>
307-
<img
308-
src={testimonial.avatarSrc}
309-
className='h-12 w-12 rounded-full'
310-
/>
311-
<div>
312-
<div className='font-semibold hover:underline'>{testimonial.name}</div>
313-
<div className='mt-1'>{testimonial.role}</div>
314-
</div>
315-
</a>
316-
</figcaption>
317-
</figure>
323+
<blockquote className='text-lg text-white sm:text-md sm:leading-8'>
324+
<p>{testimonial.quote}</p>
325+
</blockquote>
326+
<figcaption className='mt-6 text-base text-white'>
327+
<a href={testimonial.socialUrl} className='flex items-center gap-x-2'>
328+
<img src={testimonial.avatarSrc} className='h-12 w-12 rounded-full' />
329+
<div>
330+
<div className='font-semibold hover:underline'>{testimonial.name}</div>
331+
<div className='mt-1'>{testimonial.role}</div>
332+
</div>
333+
</a>
334+
</figcaption>
335+
</figure>
318336
))}
319337
</div>
320338
</div>

app/src/client/landing-page/contentSections.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,11 @@ export const features = [
3636
description: 'Graphs! Tables! Analytics w/ Plausible or Google! All in one place. Ooooooooooh.',
3737
icon: '📈',
3838
},
39+
{
40+
name: 'Blog w/ Astro',
41+
description: 'Built-in blog with the Astro framework. Write your posts in Markdown, and watch your SEO performance take off.',
42+
icon: '📝',
43+
},
3944
{
4045
name: 'Email Sending',
4146
description:

app/src/server/actions.ts

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ type GptPayload = {
5656
temperature: number;
5757
};
5858

59-
export const generateGptResponse: GenerateGptResponse<GptPayload, GptResponse> = async (
59+
export const generateGptResponse: GenerateGptResponse<GptPayload, string> = async (
6060
{ instructions, command, temperature },
6161
context
6262
) => {
@@ -105,13 +105,17 @@ export const generateGptResponse: GenerateGptResponse<GptPayload, GptResponse> =
105105
});
106106

107107
const json = (await response.json()) as OpenAIResponse;
108-
console.log('response json', json);
109-
return context.entities.GptResponse.create({
108+
console.log('response json', json?.choices[0].message.content);
109+
if (!json?.choices[0].message.content) {
110+
throw new HttpError(500, 'No response from OpenAI');
111+
}
112+
await context.entities.GptResponse.create({
110113
data: {
111114
content: json?.choices[0].message.content,
112115
user: { connect: { id: context.user.id } },
113116
},
114117
});
118+
return json?.choices[0].message.content;
115119
} catch (error: any) {
116120
if (!context.user.hasPaid && error?.statusCode != 402) {
117121
await context.entities.User.update({

0 commit comments

Comments
 (0)