
In Part 1 , we built the foundation of our AI Dream Analysis Engine. We accepted user input, cleaned the text, performed basic NLP tasks, and detected dream symbols. However, recognizing words like snake , water , or mountain isn't enough. The real intelligence begins when the system understands context, emotions, and relationships . In this part, we'll build the core AI pipeline by integrating a Large Language Model (LLM), designing production-ready prompts, implementing Retrieval-Augmented Generation (RAG), generating embeddings, and returning structured JSON responses instead of plain text. Why GPT Alone Isn't Enough Many developers build AI applications by sending a user's text directly to GPT. const response = await openai.chat.completions.create({ model: "gpt-4.1", messages: [ { role: "user", content: dream } ] }); This works—but it's not reliable enough for production. Problems include: Hallucinated interpretations No consistent response format No confidence scoring Different answers for similar dreams Difficult to integrate with applications Instead of asking GPT to "interpret this dream," we should provide structured instructions and supporting knowledge. Designing the AI Analysis Pipeline Instead of a single API call, the workflow becomes: User Dream │ ▼ Text Preprocessing │ ▼ Symbol Detection │ ▼ Emotion Analysis │ ▼ Embedding Generation │ ▼ Vector Search (Knowledge Base) │ ▼ Prompt Assembly │ ▼ GPT-4.1 │ ▼ Structured JSON Response Each stage adds context before the model generates its interpretation. Connecting the OpenAI API First, install the OpenAI SDK. npm install openai Create a reusable OpenAI client. import OpenAI from "openai"; const openai = new OpenAI({ apiKey: process.env.OPENAI_API_KEY }); export default openai; Keeping the client in a separate file allows the application to reuse a single connection. Why Prompt Engineering Matters Prompt engineering is often underestimated. Consider this prompt. Interpret this dream. The AI has almost no guidance. Now compare it with a structured system prompt. const systemPrompt = ` You are an AI Dream Analysis Assistant. Your responsibilities: - Identify important dream symbols. - Analyze emotions. - Detect recurring themes. - Explain reasoning. - Avoid predicting the future. - Avoid supernatural certainty. - Present multiple interpretations. - Mention uncertainty where appropriate. Return JSON only. `; Notice that the prompt defines behavior , not just the task. Requesting an AI Interpretation Now combine the prompt with the user's dream. const completion = await openai.chat.completions.create({ model: "gpt-4.1", temperature: 0.3, messages: [ { role: "system", content: systemPrompt }, { role: "user", content: dream } ] }); A lower temperature makes responses more consistent. For dream analysis, consistency is generally preferable to creativity. Why JSON Responses Are Better Many AI applications ask GPT to write paragraphs. That's difficult for software to process. Instead, ask for JSON. Example output: { "summary":"The dream may reflect emotional transition.", "symbols":[ "Snake", "Mountain" ], "emotion":"Fear", "themes":[ "Growth", "Anxiety" ], "confidence":0.88 } JSON allows your frontend to display each section separately. Parsing AI Responses const analysis = JSON.parse( completion.choices[0].message.content ); console.log(analysis.summary); Instead of displaying one large paragraph, your application can render: Summary Symbols Emotions Themes Confidence independently. Understanding Embeddings Dreams often contain similar meanings expressed in different words. Example 1 I was terrified by a snake. Example 2 A serpent chased me. Humans recognize these as similar. Computers do not. This is where embeddings become useful. Embeddings convert text into numerical vectors that represent semantic meaning. Creating an Embedding const embedding = await openai.embeddings.create({ model:"text-embedding-3-large", input:dream }); The returned vector might contain thousands of numbers. [0.024, -0.103, 0.887, ... 1536 values] These vectors allow similar dreams to be compared mathematically. Why Vector Databases Matter Traditional databases search exact words. Vector databases search meaning. Suppose users write: Dream A Snake chased me. Dream B A serpent followed me. A SQL search may treat these as different. A vector database understands their similarity. Popular vector databases include: Pinecone Qdrant Weaviate Milvus Saving Embeddings Example using Pinecone. await index.upsert([ { id:userId, values:embedding.data[0].embedding, metadata:{ dream } } ]); Now every analyzed dream becomes searchable. Finding Similar Dreams Later, another user submits a new dream. Generate its embedding. Search the database. const results = await index.query({ vector:embedding.data[0].embedding, topK:5, includeMetadata:true }); Instead of relying entirely on GPT's memory, we now retrieve similar dream records. What Is Retrieval-Augmented Generation (RAG)? RAG combines search with language models. Workflow: Dream ↓ Generate Embedding ↓ Search Vector Database ↓ Retrieve Similar Dreams ↓ Retrieve Symbol Articles ↓ Send Everything to GPT ↓ Generate Interpretation Rather than answering from memory alone, GPT receives supporting information first. This improves consistency and reduces hallucinations. Creating a Knowledge Base A dream engine should maintain trusted information about common symbols. Example: { "snake":[ "Transformation", "Fear", "Healing", "Renewal" ], "water":[ "Emotion", "Healing", "Uncertainty" ] } The LLM uses this information instead of inventing unsupported meanings. Combining RAG With GPT Prompt example: Dream "I dreamed a snake chased me." Relevant Knowledge Snake Possible meanings: Transformation Fear Renewal Healing Now analyze the dream using only the information above and explain your reasoning. The model becomes grounded in trusted data. Detecting Emotional Tone Symbols alone don't explain dreams. Emotion matters. Example: const emotions = [ "fear", "joy", "sadness", "anger", "hope", "anxiety" ]; GPT can identify emotional patterns. Example response: { "emotion":"Fear", "intensity":"High" } Emotion often influences interpretation more than symbolism. Returning a Structured Report Instead of displaying raw AI text, create a structured report. { "summary":"The dream reflects emotional uncertainty.", "symbols":[ "Snake", "Forest" ], "emotion":"Fear", "themes":[ "Transformation", "Personal Growth" ], "recommendation":"Reflect on recent life changes.", "confidence":91 } This format is easier to display on websites, mobile apps, and APIs. Reducing AI Hallucinations Hallucinations are one of the biggest production challenges. Several strategies help reduce them. 1. Strong System Prompts. Clearly define rules. 2. Retrieval-Augmented Generation. Provide supporting information. 3. Lower Temperature. Use values between 0.2 and 0.4. 4. Return JSON. Structured outputs reduce randomness. 5. Validate Responses. Reject malformed JSON before displaying results. Example: try{ const analysis = JSON.parse(response); }catch{ throw new Error("Invalid AI response."); } Building the Complete Analysis Function Putting everything together: async function analyzeDream(dream){ validateDream(dream); const cleaned = preprocess(dream); const embedding = await createEmbedding(cleaned); const relatedDreams = await searchVectorDB(embedding); const prompt = buildPrompt( cleaned, relatedDreams ); const result = await askGPT(prompt); return JSON.parse(result); } Notice that GPT is only one component of the pipeline. The surrounding engineering makes the system reliable. What's Coming in Part 3 So far, our engine can: Accept dream input Clean the text Detect symbols Generate embeddings Search similar dreams Retrieve trusted knowledge Query GPT Return structured JSON In Part 3 , we'll move beyond AI and build the production infrastructure behind the application. We'll design a PostgreSQL database, create REST APIs, implement JWT authentication, save dream history, optimize performance with caching, and prepare the system for deployment. By the end of the series, we'll have a complete blueprint for building a scalable AI-powered dream analysis platform rather than just another chatbot wrapped around an LLM. \
View original source — Hacker Noon ↗


