sankett commited on
Commit
df76d92
·
verified ·
1 Parent(s): 878d246

First commit

Browse files
.eslintrc.json ADDED
@@ -0,0 +1,4 @@
 
 
 
 
 
1
+ {
2
+ "extends": "next/core-web-vitals"
3
+
4
+ }
.gitignore ADDED
@@ -0,0 +1,36 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
2
+
3
+ # dependencies
4
+ /node_modules
5
+ /.pnp
6
+ .pnp.js
7
+ .yarn/install-state.gz
8
+
9
+ # testing
10
+ /coverage
11
+
12
+ # next.js
13
+ /.next/
14
+ /out/
15
+
16
+ # production
17
+ /build
18
+
19
+ # misc
20
+ .DS_Store
21
+ *.pem
22
+
23
+ # debug
24
+ npm-debug.log*
25
+ yarn-debug.log*
26
+ yarn-error.log*
27
+
28
+ # local env files
29
+ .env*.local
30
+
31
+ # vercel
32
+ .vercel
33
+
34
+ # typescript
35
+ *.tsbuildinfo
36
+ next-env.d.ts
Dockerfile.txt ADDED
@@ -0,0 +1,69 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # syntax=docker/dockerfile:1.4
2
+
3
+ # Adapted from https://github.com/vercel/next.js/blob/e60a1e747c3f521fc24dfd9ee2989e13afeb0a9b/examples/with-docker/Dockerfile
4
+ # For more information, see https://nextjs.org/docs/pages/building-your-application/deploying#docker-image
5
+
6
+ FROM node:18 AS base
7
+
8
+ # Install dependencies only when needed
9
+ FROM base AS deps
10
+ WORKDIR /app
11
+
12
+ # Install dependencies based on the preferred package manager
13
+ COPY --link package.json yarn.lock* package-lock.json* pnpm-lock.yaml* ./
14
+ RUN \
15
+ if [ -f yarn.lock ]; then yarn --frozen-lockfile; \
16
+ elif [ -f package-lock.json ]; then npm ci; \
17
+ elif [ -f pnpm-lock.yaml ]; then yarn global add pnpm && pnpm i --frozen-lockfile; \
18
+ else echo "Lockfile not found." && exit 1; \
19
+ fi
20
+
21
+
22
+ # Rebuild the source code only when needed
23
+ FROM base AS builder
24
+ WORKDIR /app
25
+ COPY --from=deps --link /app/node_modules ./node_modules
26
+ COPY --link . .
27
+
28
+ # Next.js collects completely anonymous telemetry data about general usage.
29
+ # Learn more here: https://nextjs.org/telemetry
30
+ # Uncomment the following line in case you want to disable telemetry during the build.
31
+ # ENV NEXT_TELEMETRY_DISABLED 1
32
+
33
+ RUN npm run build
34
+
35
+ # If using yarn comment out above and use below instead
36
+ # RUN yarn build
37
+
38
+ # Production image, copy all the files and run next
39
+ FROM base AS runner
40
+ WORKDIR /app
41
+
42
+ ENV NODE_ENV production
43
+ # Uncomment the following line in case you want to disable telemetry during runtime.
44
+ # ENV NEXT_TELEMETRY_DISABLED 1
45
+
46
+ RUN \
47
+ addgroup --system --gid 1001 nodejs; \
48
+ adduser --system --uid 1001 nextjs
49
+
50
+ COPY --from=builder --link /app/public ./public
51
+
52
+ # Automatically leverage output traces to reduce image size
53
+ # https://nextjs.org/docs/advanced-features/output-file-tracing
54
+ COPY --from=builder --link --chown=1001:1001 /app/.next/standalone ./
55
+ COPY --from=builder --link --chown=1001:1001 /app/.next/static ./.next/static
56
+
57
+ USER nextjs
58
+
59
+ EXPOSE 3000
60
+
61
+ ENV PORT 3000
62
+ ENV HOSTNAME 0.0.0.0
63
+
64
+ # Allow the running process to write model files to the cache folder.
65
+ # NOTE: In practice, you would probably want to pre-download the model files to avoid having to download them on-the-fly.
66
+ RUN mkdir -p /app/node_modules/@xenova/.cache/
67
+ RUN chmod 777 -R /app/node_modules/@xenova/
68
+
69
+ CMD ["node", "server.js"]
README.md CHANGED
@@ -1,10 +1,36 @@
1
- ---
2
- title: Gen Ui
3
- emoji: 👁
4
- colorFrom: indigo
5
- colorTo: indigo
6
- sdk: docker
7
- pinned: false
8
- ---
9
-
10
- Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ This is a [Next.js](https://nextjs.org/) project bootstrapped with [`create-next-app`](https://github.com/vercel/next.js/tree/canary/packages/create-next-app).
2
+
3
+ ## Getting Started
4
+
5
+ First, run the development server:
6
+
7
+ ```bash
8
+ npm run dev
9
+ # or
10
+ yarn dev
11
+ # or
12
+ pnpm dev
13
+ # or
14
+ bun dev
15
+ ```
16
+
17
+ Open [http://localhost:3000](http://localhost:3000) with your browser to see the result.
18
+
19
+ You can start editing the page by modifying `app/page.tsx`. The page auto-updates as you edit the file.
20
+
21
+ This project uses [`next/font`](https://nextjs.org/docs/basic-features/font-optimization) to automatically optimize and load Inter, a custom Google Font.
22
+
23
+ ## Learn More
24
+
25
+ To learn more about Next.js, take a look at the following resources:
26
+
27
+ - [Next.js Documentation](https://nextjs.org/docs) - learn about Next.js features and API.
28
+ - [Learn Next.js](https://nextjs.org/learn) - an interactive Next.js tutorial.
29
+
30
+ You can check out [the Next.js GitHub repository](https://github.com/vercel/next.js/) - your feedback and contributions are welcome!
31
+
32
+ ## Deploy on Vercel
33
+
34
+ The easiest way to deploy your Next.js app is to use the [Vercel Platform](https://vercel.com/new?utm_medium=default-template&filter=next.js&utm_source=create-next-app&utm_campaign=create-next-app-readme) from the creators of Next.js.
35
+
36
+ Check out our [Next.js deployment documentation](https://nextjs.org/docs/deployment) for more details.
app/actions/conversations.tsx ADDED
@@ -0,0 +1,74 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use server';
2
+
3
+ import { generateText, streamObject } from 'ai';
4
+ import { openai } from '@ai-sdk/openai';
5
+ import { createStreamableUI } from 'ai/rsc';
6
+ import { ReactNode } from 'react';
7
+ import { z } from 'zod';
8
+ import { Product } from '../components/product';
9
+
10
+ export interface Message {
11
+ role: 'user' | 'assistant';
12
+ content: string;
13
+ display?: ReactNode; // [!code highlight]
14
+ }
15
+
16
+ export async function Conversations(history: Message[]) {
17
+ const stream = createStreamableUI(<div>Loadiing..</div>);
18
+
19
+ const { text, toolResults } = await generateText({
20
+ model: openai('gpt-4o'),
21
+ system: 'You are a friendly weather assistant!',
22
+ messages: history,
23
+ tools: {
24
+ showWeather: {
25
+ description: 'Show the weather for a given location.',
26
+ parameters: z.object({
27
+ city: z.string().describe('The city to show the weather for.'),
28
+ unit: z
29
+ .enum(['C', 'F'])
30
+ .describe('The unit to display the temperature in'),
31
+ }),
32
+ execute: async ({ city, unit }) => {
33
+ stream.done(
34
+ <div>
35
+ {city}-{unit}{' '}
36
+ </div>
37
+ );
38
+ return `Here's the weather for ${city}!`;
39
+ },
40
+ },
41
+ showCategory: {
42
+ description: 'Show the product details for a category.',
43
+ parameters: z.object({
44
+ value: z.string().describe('The value.'),
45
+ }),
46
+ execute: async ({ value }) => {
47
+ const response = await fetch(
48
+ `https://fakestoreapi.com/products/category/${value}`
49
+ ).then((res) => res.json());
50
+
51
+ stream.done(
52
+ <div>
53
+ <Product productlist={response} />
54
+ </div>
55
+ );
56
+ return `Here's the category details! ${value}`;
57
+ },
58
+ },
59
+ },
60
+ });
61
+
62
+ console.log('history', history);
63
+ return {
64
+ messages: [
65
+ ...history,
66
+ {
67
+ role: 'assistant' as const,
68
+ content:
69
+ text || toolResults.map((toolResult) => toolResult.result).join(),
70
+ display: stream.value,
71
+ },
72
+ ],
73
+ };
74
+ }
app/actions/mixedstate.tsx ADDED
@@ -0,0 +1,40 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import { createAI, getAIState,createStreamableUI, streamUI } from 'ai/rsc';
2
+ import { ReactNode } from 'react';
3
+ import { openai } from '@ai-sdk/openai';
4
+ import { generateText } from 'ai';
5
+ export type AIState = Array<{
6
+ role: 'user' | 'assistant';
7
+ content: string;
8
+ }>;
9
+
10
+ export type UIState = Array<{
11
+ id: string;
12
+ role: 'user' | 'assistant';
13
+ display: ReactNode;
14
+ }>;
15
+
16
+ async function sendMessage(message: string) {
17
+ 'use server';
18
+
19
+ const stream = createStreamableUI(<div>Loading..</div>);
20
+
21
+ const history:any = getAIState();
22
+ const response = await generateText({
23
+ model: openai('gpt-4o'),
24
+ messages: [...history, { role: 'user', content: message }],
25
+ });
26
+
27
+
28
+ stream.done(<div style={{fontSize: "14px"}}>{response.text}</div>);
29
+
30
+
31
+ return { text: response.text, display: stream.value};
32
+ }
33
+
34
+ export const AI = createAI({
35
+ initialAIState: [] as AIState,
36
+ initialUIState: [] as UIState,
37
+ actions: {
38
+ sendMessage,
39
+ },
40
+ });
app/actions/mixeduistate.tsx ADDED
@@ -0,0 +1,151 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use server';
2
+
3
+ import {
4
+ createAI,
5
+ getMutableAIState,
6
+ streamUI,
7
+ createStreamableUI,
8
+ } from 'ai/rsc';
9
+ import { openai } from '@ai-sdk/openai';
10
+ import { ReactNode } from 'react';
11
+ import { z } from 'zod';
12
+ import { nanoid } from 'nanoid';
13
+ import { streamObject } from 'ai';
14
+ import { NotificationSchema } from './notificationobject';
15
+ import { Partial } from '../components/partial';
16
+ import { Product } from '../components/product';
17
+
18
+ export interface ServerMessage {
19
+ role: 'user' | 'assistant';
20
+ content: string;
21
+ }
22
+
23
+ export interface ClientMessage {
24
+ id: string;
25
+ role: 'user' | 'assistant';
26
+ display: ReactNode;
27
+ }
28
+
29
+ export async function sendMessage1(input: string): Promise<ClientMessage> {
30
+ 'use server';
31
+
32
+ //const partialComponent = createStreamableUI(<div>Loading...</div>);
33
+ const history: any = getMutableAIState();
34
+ const result = await streamUI({
35
+ model: openai('gpt-4o'),
36
+ messages: [...history.get(), { role: 'user', content: input }],
37
+ text: ({ content, done }) => {
38
+ if (done) {
39
+ console.log('done', content);
40
+ history.done((messages: ServerMessage[]) => [
41
+ ...messages,
42
+ { role: 'assistant', content },
43
+ ]);
44
+ }
45
+
46
+ return <div>{content}-22</div>;
47
+ },
48
+
49
+ tools: {
50
+ showCategory: {
51
+ description: 'Show the product details for a category.',
52
+ parameters: z.object({
53
+ value: z.string().describe('The value.'),
54
+ }),
55
+ generate: async ({ value }) => {
56
+ console.log('value', value);
57
+ const response = await fetch(
58
+ `https://fakestoreapi.com/products/category/${value}`
59
+ ).then((res) => res.json());
60
+
61
+ return (
62
+ <div>
63
+ {response.length > 0 ? (
64
+ <Product productlist={response} />
65
+ ) : (
66
+ `No products found for ${value}`
67
+ )}
68
+ </div>
69
+ );
70
+
71
+ },
72
+ },
73
+ showWeather: {
74
+ description: 'Show the weather for a given location.',
75
+ parameters: z.object({
76
+ city: z.string().describe('The city to show the weather for.'),
77
+ unit: z
78
+ .enum(['C', 'F'])
79
+ .describe("The unit to display the temperature in"),
80
+ }),
81
+ generate: async ({ city, unit }) => {
82
+ return <div>Heres the weather</div>;
83
+ },
84
+ },
85
+ chart: {
86
+ description:
87
+ 'You generate specified output for specified duration and show graph type e.g. line,bar',
88
+ parameters: z.object({
89
+ charttype: z
90
+ .string()
91
+ .describe('The type of the chart, example: line, bar, pie, etc.'),
92
+ }),
93
+ generate: async function* ({ charttype }) {
94
+ yield (
95
+ <div style={{ color: 'yellow', fontSize: '16px' }}>
96
+ Preparing for {charttype}...
97
+ </div>
98
+ ); // [!code highlight:5]
99
+ await new Promise((resolve) => setTimeout(resolve, 1200));
100
+ yield (
101
+ <div style={{ color: 'yellow', fontSize: '16px' }}>
102
+ Getting data for {charttype}...
103
+ </div>
104
+ );
105
+ await new Promise((resolve) => setTimeout(resolve, 1200));
106
+
107
+ const { partialObjectStream } = await streamObject({
108
+ model: openai('gpt-4o'),
109
+ system:
110
+ 'You generate specified output for specified months in India.',
111
+ prompt: input,
112
+ schema: NotificationSchema,
113
+ });
114
+ //const arr =[]
115
+ let data;
116
+ for await (const partialObject of partialObjectStream) {
117
+ yield (
118
+ <div className="w-full xs:w-4/5 sm:w-4/5 lg:w-2/5">
119
+ <Partial partialObject={partialObject} charttype={charttype} />
120
+ </div>
121
+ );
122
+ data = partialObject;
123
+ //arr.push(partialObject);
124
+ }
125
+ //partialComponent.done();
126
+ return (
127
+ <div className="w-full xs:w-4/5 sm:w-4/5 lg:w-2/5 ">
128
+ <Partial partialObject={data} charttype={charttype} />
129
+ </div>
130
+ );
131
+
132
+ //return <div style={{color: "green", width: "50%"}}>{repositoryName} deployed! <Partial partialObject={arr[arr.length-1]} /></div>;
133
+ },
134
+ },
135
+ },
136
+ });
137
+
138
+ return {
139
+ id: nanoid(),
140
+ role: 'assistant',
141
+ display: result.value,
142
+ };
143
+ }
144
+
145
+ export const AI1: any = createAI<ServerMessage[], ClientMessage[]>({
146
+ actions: {
147
+ sendMessage1,
148
+ },
149
+ initialAIState: [],
150
+ initialUIState: [],
151
+ });
app/actions/notificationobject.ts ADDED
@@ -0,0 +1,13 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import { z } from 'zod';
2
+ import { DeepPartial } from 'ai';
3
+ export const NotificationSchema = z.object({
4
+ notifications:
5
+ z.object({
6
+ label: z.string(),
7
+ months: z.array(z.string()),
8
+ rates: z.array(z.number()),
9
+ })
10
+
11
+ })
12
+
13
+ export type PartialNotification = DeepPartial<typeof NotificationSchema>;
app/actions/notifications.tsx ADDED
@@ -0,0 +1,37 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use server';
2
+
3
+ import { streamObject } from 'ai';
4
+ import { openai } from '@ai-sdk/openai';
5
+ import { createStreamableValue, createStreamableUI } from 'ai/rsc';
6
+ import { z } from 'zod';
7
+ import { NotificationSchema } from './notificationobject';
8
+ import { Partial } from '../components/partial';
9
+
10
+ export async function Notifications(input: string) {
11
+ 'use server';
12
+
13
+ const stream = createStreamableValue();
14
+ const partialComponent = createStreamableUI(<div>Loading...</div>);
15
+
16
+ (async () => {
17
+ const { partialObjectStream } = await streamObject({
18
+ model: openai('gpt-4o'),
19
+ system: 'You generate specified output for specified months in India.',
20
+ prompt: input,
21
+ schema: NotificationSchema,
22
+ });
23
+
24
+ //let messages = [{ role: 'user', content: "user1" }, { role: 'assistant', content: "assistant1..." },{ role: 'user', content: "user2" }, { role: 'assistant', content: "" }];
25
+
26
+ for await (const partialObject of partialObjectStream) {
27
+ partialComponent.update(<Partial partialObject={partialObject} charttype='line' />);
28
+ //messages = [...messages, { role: 'assistant', content: partialObject.notifications }];
29
+ stream.update(partialObject);
30
+ }
31
+ //console.log(JSON.stringify(messages));
32
+ partialComponent.done();
33
+ stream.done();
34
+ })();
35
+
36
+ return { object: stream.value, notificationComponent: partialComponent.value, };
37
+ }
app/components/chart/linechart.tsx ADDED
@@ -0,0 +1,72 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ "use client"
2
+
3
+ import {useState} from 'react';
4
+ import { Line, Bar } from 'react-chartjs-2';
5
+ import {
6
+ Chart as ChartJS,
7
+ CategoryScale,
8
+ LinearScale,
9
+ PointElement,
10
+ LineElement,
11
+ Title,
12
+ Tooltip,
13
+ Legend,
14
+ BarElement
15
+ } from 'chart.js';
16
+
17
+ ChartJS.register(
18
+ CategoryScale,
19
+ LinearScale,
20
+ PointElement,
21
+ LineElement,
22
+ Title,
23
+ Tooltip,
24
+ Legend,
25
+ BarElement
26
+ );
27
+
28
+ export const LineChart = ( {lineChartData, charttype}) => {
29
+ //const [tempData, setTempdata] = useState(lineChartData);
30
+ const data = {
31
+ labels: lineChartData.labels,
32
+ datasets: [
33
+ {
34
+ label: lineChartData.label ??'Gold Price (INR per 10 gm)',
35
+ data:lineChartData.data,
36
+ borderColor: 'rgba(75,192,192,1)',
37
+ backgroundColor: 'rgba(75,192,192,1)',
38
+ fill: true,
39
+ },
40
+ ],
41
+ };
42
+
43
+ const options:any = {
44
+ responsive: true,
45
+ plugins: {
46
+ legend: {
47
+ position: 'top',
48
+ },
49
+ title: {
50
+ display: true,
51
+ text: lineChartData.label ?? 'Gold Price (INR per 10 gm) from July to December 2023',
52
+ },
53
+ },
54
+ scales: {
55
+ x: {
56
+ ticks: {
57
+ color: 'yellow', // Change x-axis label color
58
+ },
59
+ },
60
+ y: {
61
+ beginAtZero: false,
62
+ ticks: {
63
+ color: 'yellow', // Change x-axis label color
64
+ },
65
+ },
66
+ },
67
+ };
68
+
69
+ return charttype == "line" ? <Line data={data} options={options} /> : <Bar data={data} options={options} />;
70
+ };
71
+
72
+
app/components/mixedcomponent.tsx ADDED
@@ -0,0 +1,38 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use client';
2
+
3
+ import { useActions, useAIState } from 'ai/rsc';
4
+ import { AI } from '../actions/mixedstate';
5
+
6
+ export default function MixedComponent() {
7
+ const { sendMessage } = useActions<typeof AI>();
8
+ const [messages, setMessages] = useAIState<typeof AI>();
9
+
10
+ const handleSubmit = async event => {
11
+ event.preventDefault();
12
+
13
+ setMessages([
14
+ ...messages,
15
+ { role: 'user', content: event.target.message.value },
16
+ ]);
17
+ const {text, display} = await sendMessage(event.target.message.value);
18
+ console.log(display);
19
+ setMessages((messages) => [...messages, { role: 'assistant', content: text }])
20
+ };
21
+
22
+ return (
23
+ <>
24
+ <ul>
25
+ {messages.map((message,index) => (
26
+ <li key={index}>{message.role}:{message.content}
27
+ <br></br>
28
+
29
+ </li>
30
+ ))}
31
+ </ul>
32
+ <form onSubmit={handleSubmit}>
33
+ <input type="text" name="message" />
34
+ <button type="submit">Send</button>
35
+ </form>
36
+ </>
37
+ );
38
+ }
app/components/mixeduicomponent.tsx ADDED
@@ -0,0 +1,81 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use client';
2
+ //MixedUIComponent
3
+
4
+ import { useState } from 'react';
5
+ import { ClientMessage } from '../actions/mixeduistate';
6
+ import { useActions, useUIState } from 'ai/rsc';
7
+ import { nanoid } from 'nanoid';
8
+
9
+ export default function Home() {
10
+ const [input, setInput] = useState<string>('Gold price in India from Jan to Jun 2023');
11
+ const [conversation, setConversation] = useUIState();
12
+ const { sendMessage1 } = useActions();
13
+ const [selectedValue, setSelectedValue] = useState('');
14
+ const handleChange =async (event) => {
15
+ if(event.target.value === ''){
16
+ return;
17
+ }
18
+ setSelectedValue(event.target.value);
19
+
20
+ setConversation((currentConversation: ClientMessage[]) => [
21
+ ...currentConversation,
22
+ { id: nanoid(), role: 'user', display: event.target.value },
23
+ ]);
24
+
25
+ const message = await sendMessage1(event.target.value);
26
+
27
+ setConversation((currentConversation: ClientMessage[]) => [
28
+ ...currentConversation,
29
+ message,
30
+ ]);
31
+ };
32
+ return (
33
+ <div className="h-screen bg-gray-900 text-white flex-col items-center">
34
+ <div className="bg-gray-800 w-7/8 max-w-8xl h-5/6 overflow-y-auto ">
35
+ {conversation.map(
36
+ (message: ClientMessage) => (
37
+ console.log('message', typeof message.display),
38
+ (
39
+ <div
40
+ key={message.id}
41
+ className={`inline-block px-3 py-2 text-sm
42
+ ${
43
+ message.role === 'user' ? 'bg-blue-600' : 'bg-black-600'
44
+ } w-full max-w-8xl `}
45
+ >
46
+ <pre> {message.display}</pre>
47
+ </div>
48
+ )
49
+ )
50
+ )}
51
+ </div>
52
+
53
+ <div>
54
+ <div className="w-full max-w-xs my-2 ">
55
+
56
+ <select
57
+ id="select"
58
+ value={selectedValue}
59
+ onChange={handleChange}
60
+ className=" bg-gray-700 border-none text-white text-xs px-4 py-2
61
+ w-full border border-gray-400 hover:border-gray-500"
62
+ >
63
+ <option value="" disabled>
64
+ Select an option
65
+ </option>
66
+ <option value="Longest 5 rivers in world">Longest 5 rivers in world</option>
67
+ <option value="Gold price in India from Jan to Jun 2023 draw line chart">Gold price in India from Jan to Jun 2023 draw line chart</option>
68
+ <option value="Get products for electronics">Get products for electronics</option>
69
+ <option value="Show me products for jewelery">Show me products for jewelery</option>
70
+ <option value="Recipe of Pizza">Recipe of Pizza</option>
71
+ <option value="List out products for men\'s clothing">List out products for mens clothing</option>
72
+ <option value="For women\'s clothing list all products">For womens clothing list all products</option>
73
+ <option value="Population in India from Year 2010 to 2023 draw bar chart">Population in India from Year 2010 to 2023 draw bar chart</option>
74
+
75
+ </select>
76
+
77
+ </div>
78
+ </div>
79
+ </div>
80
+ );
81
+ }
app/components/notificationapp.tsx ADDED
@@ -0,0 +1,47 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use client';
2
+
3
+ import { useState } from 'react';
4
+ import { Notifications } from '../actions/notifications';
5
+ import { readStreamableValue } from 'ai/rsc';
6
+
7
+ export function Notificationapp() {
8
+ const [generation, setGeneration] = useState<string>('');
9
+ const [notify, setNotify] = useState<any>(null);
10
+ const [text, setText] = useState("Gold Price in India per 10 gm duration Jan 2022 to Dec 2022");
11
+ const onTextChange = (e) => {
12
+ setText(e.target.value);
13
+ }
14
+
15
+ return (
16
+ <div>
17
+ <input type="text" value={text} style={{width: "500px"}} onChange={onTextChange} />
18
+ <button
19
+ onClick={async () => {
20
+ const { object, notificationComponent } = await Notifications(text);
21
+ setNotify(notificationComponent)
22
+ for await (const partialObject of readStreamableValue(object)) {
23
+ if (partialObject) {
24
+
25
+ setGeneration(
26
+ JSON.stringify(partialObject.notifications, null, 2),
27
+ );
28
+ }
29
+ }
30
+ }}
31
+ >
32
+ Show
33
+ </button>
34
+
35
+ <div className="flex flex-row">
36
+ <div className="basis-1/2 border-dotted border-2 border-slate-600 rounded-md">
37
+ <div className='w-3/4 text-sm'>
38
+ <pre>{generation}</pre>
39
+ </div>
40
+ </div>
41
+ <div className="basis-1/2 border-dotted border-2 border-indigo-600 rounded-md text-sm">
42
+ {notify}
43
+ </div>
44
+ </div>
45
+ </div>
46
+ )
47
+ }
app/components/partial.tsx ADDED
@@ -0,0 +1,36 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+
2
+
3
+ import { PartialNotification } from '../actions/notificationobject';
4
+ import { LineChart } from './chart/linechart';
5
+
6
+ export function Partial({
7
+ partialObject,
8
+ charttype,
9
+ }: {
10
+ partialObject?: PartialNotification,
11
+ charttype: string,
12
+ }) {
13
+
14
+ let lineData = {
15
+ label: "",
16
+ labels: [],
17
+ data: [],
18
+ }
19
+ if(!partialObject.notifications){
20
+ lineData.labels = [];
21
+ lineData.data = [];
22
+ }
23
+ else{
24
+ lineData.label = partialObject.notifications?.label;
25
+ lineData.labels = partialObject.notifications?.months;
26
+ lineData.data = partialObject.notifications?.rates;
27
+ }
28
+ return (
29
+ <div>
30
+
31
+
32
+ {lineData.labels && lineData.labels.length > 0 && <LineChart lineChartData={lineData} charttype={charttype} />}
33
+
34
+ </div>
35
+ );
36
+ }
app/components/product.tsx ADDED
@@ -0,0 +1,23 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+
2
+ export function Product({productlist}){
3
+ return (
4
+ <div>
5
+ <table className="table-fixed border-collapse border border-slate-400 p-4">
6
+ <th className="text-left p-1 pl-4">Category</th>
7
+ <th className="text-left p-1 pl-4">Title</th>
8
+ <th className="text-left p-1 pl-4">Price</th>
9
+ <th className="text-left p-1 pl-4 "></th>
10
+
11
+ {productlist.map((product, index) => (
12
+ <tr key={index} className="text-left p-1">
13
+ <td className="text-left p-1 pl-4">{product.category}</td>
14
+ <td className="text-left p-1 pl-4">{product.title}</td>
15
+ <td className="text-left p-1 pl-4">{product.price}</td>
16
+ <td className="text-left p-1 pl-4"><button type="button" className="text-white bg-blue-700 hover:bg-blue-800 focus:ring-4 focus:ring-blue-300 font-medium rounded-lg text-sm px-5 py-1 me-2 mb-2 dark:bg-blue-600 dark:hover:bg-blue-700 focus:outline-none dark:focus:ring-blue-800">Remove</button></td>
17
+ </tr>
18
+ ))}
19
+ </table>
20
+ </div>
21
+ )
22
+
23
+ }
app/components/weatherconversations.tsx ADDED
@@ -0,0 +1,46 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use client';
2
+
3
+ import { useState } from 'react';
4
+ import { Message, Conversations } from '../actions/conversations';
5
+
6
+ export default function WeatherConversations() {
7
+ const [conversation, setConversation] = useState<Message[]>([]);
8
+ const [input, setInput] = useState<string>('get products for electronics');
9
+
10
+ const textChange = async (event) => {
11
+ setInput(event.target.value);
12
+ };
13
+
14
+ const sendMessage = async () => {
15
+ const { messages } = await Conversations([
16
+ ...conversation.map(({ role, content }) => ({ role, content })),
17
+ { role: 'user', content: input }
18
+ ]);
19
+ setConversation(messages);
20
+ };
21
+
22
+ return (
23
+ <div >
24
+ <div>
25
+ {conversation.map((message, index) => (
26
+ <div key={index} className='grid grid-cols-1'>
27
+ {message.role}: {message.content}
28
+ {message.display}
29
+ </div>
30
+ ))}
31
+ </div>
32
+
33
+ <div>
34
+ <input
35
+ type="text"
36
+ value={input}
37
+ onChange={textChange}
38
+ className='bg-white dark:bg-slate-800'
39
+ />
40
+ <button onClick= {sendMessage}>
41
+ Send Message
42
+ </button>
43
+ </div>
44
+ </div>
45
+ );
46
+ }
app/favicon.ico ADDED
app/globals.css ADDED
@@ -0,0 +1,33 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ @tailwind base;
2
+ @tailwind components;
3
+ @tailwind utilities;
4
+
5
+ :root {
6
+ --foreground-rgb: 0, 0, 0;
7
+ --background-start-rgb: 214, 219, 220;
8
+ --background-end-rgb: 255, 255, 255;
9
+ }
10
+
11
+ @media (prefers-color-scheme: dark) {
12
+ :root {
13
+ --foreground-rgb: 255, 255, 255;
14
+ --background-start-rgb: 0, 0, 0;
15
+ --background-end-rgb: 0, 0, 0;
16
+ }
17
+ }
18
+
19
+ body {
20
+ color: rgb(var(--foreground-rgb));
21
+ background: linear-gradient(
22
+ to bottom,
23
+ transparent,
24
+ rgb(var(--background-end-rgb))
25
+ )
26
+ rgb(var(--background-start-rgb));
27
+ }
28
+
29
+ @layer utilities {
30
+ .text-balance {
31
+ text-wrap: balance;
32
+ }
33
+ }
app/layout.tsx ADDED
@@ -0,0 +1,22 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import type { Metadata } from "next";
2
+ import { Inter } from "next/font/google";
3
+ import "./globals.css";
4
+
5
+ const inter = Inter({ subsets: ["latin"] });
6
+
7
+ export const metadata: Metadata = {
8
+ title: "Create Next App",
9
+ description: "Generated by create next app",
10
+ };
11
+
12
+ export default function RootLayout({
13
+ children,
14
+ }: Readonly<{
15
+ children: React.ReactNode;
16
+ }>) {
17
+ return (
18
+ <html lang="en" className="">
19
+ <body className={inter.className}>{children}</body>
20
+ </html>
21
+ );
22
+ }
app/page.tsx ADDED
@@ -0,0 +1,29 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import dynamic from 'next/dynamic';
2
+ import { Notificationapp } from './components/notificationapp';
3
+ import WeatherConversations from './components/weatherconversations';
4
+ import { AI } from './actions/mixedstate';
5
+ import { AI1 } from './actions/mixeduistate';
6
+ import MixedComponent from './components/mixedcomponent';
7
+ import MixedUIComponent from './components/mixeduicomponent';
8
+ import Image from 'next/image';
9
+ const LineChart = dynamic((): any => import('./components/chart/linechart'), {
10
+ ssr: false,
11
+ });
12
+
13
+ export default function Home() {
14
+ return (
15
+ <main className="min-h-screen flex-col items-center justify-between bg-white dark:bg-slate-800 text-slate-900 dark:text-white">
16
+ <header className="bg-gray-800 w-full py-1 border-b border-white">
17
+ <span className="text-left text-yellow-500 text-2xl font-bold-100 pl-2 inline w-full">
18
+ Generative UI Demo with AI
19
+ </span>
20
+ <sup className="text-white ml-3 italic"> By Sanket Terdal</sup>
21
+ </header>
22
+ <div className="flex-1">
23
+ <AI1>
24
+ <MixedUIComponent />
25
+ </AI1>
26
+ </div>
27
+ </main>
28
+ );
29
+ }
next-env.d.ts ADDED
@@ -0,0 +1,5 @@
 
 
 
 
 
 
1
+ /// <reference types="next" />
2
+ /// <reference types="next/image-types/global" />
3
+
4
+ // NOTE: This file should not be edited
5
+ // see https://nextjs.org/docs/basic-features/typescript for more information.
next.config.mjs ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
 
1
+ /** @type {import('next').NextConfig} */
2
+ const nextConfig = {
3
+ images: {
4
+ domains: ['storybook7.blob.core.windows.net'],
5
+ },
6
+ };
7
+
8
+ export default nextConfig;
package.json ADDED
@@ -0,0 +1,33 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "name": "genui-demo",
3
+ "version": "0.1.0",
4
+ "private": true,
5
+ "scripts": {
6
+ "dev": "cross-env NODE_TLS_REJECT_UNAUTHORIZED=0 next dev",
7
+ "build": "next build",
8
+ "start": "cross-env NODE_TLS_REJECT_UNAUTHORIZED=0 next start",
9
+ "lint": "next lint"
10
+ },
11
+ "dependencies": {
12
+ "@ai-sdk/openai": "^0.0.17",
13
+ "ai": "^3.1.18",
14
+ "chart.js": "^4.4.3",
15
+ "cross-env": "^7.0.3",
16
+ "nanoid": "^5.0.7",
17
+ "next": "14.2.3",
18
+ "react": "^18",
19
+ "react-chartjs-2": "^5.2.0",
20
+ "react-dom": "^18",
21
+ "zod": "^3.23.8"
22
+ },
23
+ "devDependencies": {
24
+ "@types/node": "^20",
25
+ "@types/react": "^18",
26
+ "@types/react-dom": "^18",
27
+ "eslint": "^8",
28
+ "eslint-config-next": "14.2.3",
29
+ "postcss": "^8",
30
+ "tailwindcss": "^3.4.1",
31
+ "typescript": "^5"
32
+ }
33
+ }
pnpm-lock.yaml ADDED
The diff for this file is too large to render. See raw diff
 
postcss.config.mjs ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
 
1
+ /** @type {import('postcss-load-config').Config} */
2
+ const config = {
3
+ plugins: {
4
+ tailwindcss: {},
5
+ },
6
+ };
7
+
8
+ export default config;
public/next.svg ADDED
public/vercel.svg ADDED
tailwind.config.ts ADDED
@@ -0,0 +1,21 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import type { Config } from "tailwindcss";
2
+
3
+ const config: Config = {
4
+ darkMode: 'selector',
5
+ content: [
6
+ "./pages/**/*.{js,ts,jsx,tsx,mdx}",
7
+ "./components/**/*.{js,ts,jsx,tsx,mdx}",
8
+ "./app/**/*.{js,ts,jsx,tsx,mdx}",
9
+ ],
10
+ theme: {
11
+ extend: {
12
+ backgroundImage: {
13
+ "gradient-radial": "radial-gradient(var(--tw-gradient-stops))",
14
+ "gradient-conic":
15
+ "conic-gradient(from 180deg at 50% 50%, var(--tw-gradient-stops))",
16
+ },
17
+ },
18
+ },
19
+ plugins: [],
20
+ };
21
+ export default config;
tsconfig.json ADDED
@@ -0,0 +1,26 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "compilerOptions": {
3
+ "lib": ["dom", "dom.iterable", "esnext"],
4
+ "allowJs": true,
5
+ "skipLibCheck": true,
6
+ "strict": false,
7
+ "noEmit": true,
8
+ "esModuleInterop": true,
9
+ "module": "esnext",
10
+ "moduleResolution": "bundler",
11
+ "resolveJsonModule": true,
12
+ "isolatedModules": true,
13
+ "jsx": "preserve",
14
+ "incremental": true,
15
+ "plugins": [
16
+ {
17
+ "name": "next"
18
+ }
19
+ ],
20
+ "paths": {
21
+ "@/*": ["./*"]
22
+ }
23
+ },
24
+ "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
25
+ "exclude": ["node_modules"]
26
+ }