A complete step-by-step guide to building a functional weather application using vibe coding techniques.
This guide will walk you through creating a functional weather application using Cursor AI and vibe coding techniques. By the end, you'll have built a practical web application that displays weather information for any location - all without needing to write code manually!
Before starting this project, ensure you have:
Launch Cursor and create a new folder for your weather app project. You can do this by clicking on "File" > "New Folder" or using the file explorer in Cursor.
Vibe Coding Tip:
When starting a new project, it's helpful to create a dedicated folder to keep all your files organized. This makes it easier to manage your project as it grows.
In your project folder, create a new file named app.py
. This will be the main file for your weather application.
Vibe Coding Tip:
The .py
extension indicates this is a Python file. We'll be using Python with Streamlit, a library that makes it easy to create web applications.
Open the Composer in Cursor (using Ctrl/Cmd+K) and enter the following prompt:
I want to create a weather app using Python and Streamlit. The app should allow users to search for a city and display the current weather conditions including temperature, humidity, wind speed, and a description of the weather. Please set up the basic structure of the app with necessary imports and a simple UI.
Vibe Coding Tip:
Be specific in your prompts to get better results. Mention the programming language, libraries, and features you want to include.
Cursor will generate code based on your prompt. Review it to make sure it includes the necessary imports and basic structure, then click "Apply" to add it to your file.
import streamlit as st import requests import json from datetime import datetime # Set page configuration st.set_page_config( page_title="Weather App", page_icon="🌤️", layout="centered" ) # App title and description st.title("Weather App") st.write("Search for a city to get the current weather conditions") # Input for city name city = st.text_input("Enter city name:", "")
Vibe Coding Tip:
Always review the generated code before applying it. This helps you understand what the AI is doing and allows you to make adjustments if needed.
Open the Composer (Ctrl/Cmd+K) and enter this prompt to add API integration:
I need to integrate a free weather API into my app. Please add code to fetch weather data from OpenWeatherMap API when a user enters a city name. The app should display temperature in both Celsius and Fahrenheit, humidity, wind speed, and weather description. Also add error handling for cases when the city is not found or there are API issues.
To use the OpenWeatherMap API, you'll need to get a free API key:
Vibe Coding Tip:
Many web services require API keys for access. These keys are like passwords that allow your application to use the service. Always keep your API keys secure and never share them publicly.
After applying the generated code, find the API key section and replace it with your own key:
# API key for OpenWeatherMap api_key = "your_api_key_here" # Replace with your actual API key
The generated code should include a function to fetch weather data from the API:
def get_weather_data(city_name, api_key): base_url = "http://api.openweathermap.org/data/2.5/weather?" complete_url = f"{base_url}q={city_name}&appid={api_key}&units=metric" response = requests.get(complete_url) return response.json()
Vibe Coding Tip:
This function makes an HTTP request to the OpenWeatherMap API and returns the weather data in JSON format. The units=metric
parameter ensures temperatures are returned in Celsius.
Open the Composer (Ctrl/Cmd+K) and enter this prompt to improve the user interface:
I want to improve the user interface of my weather app. Please add: 1. A nice header with a weather icon 2. A card layout for displaying weather information 3. Icons for different weather conditions 4. Color coding based on temperature 5. A loading spinner while fetching data
The AI will generate code to improve the UI. Review it and click "Apply" to update your file.
# Display weather information in a nice card def display_weather_card(weather_data): # Extract data temp_c = weather_data["main"]["temp"] temp_f = (temp_c * 9/5) + 32 humidity = weather_data["main"]["humidity"] wind_speed = weather_data["wind"]["speed"] description = weather_data["weather"][0]["description"] icon_code = weather_data["weather"][0]["icon"] # Create columns for layout col1, col2 = st.columns(2) with col1: st.metric("Temperature", f"{temp_c:.1f}°C / {temp_f:.1f}°F") st.metric("Humidity", f"{humidity}%") with col2: st.metric("Wind Speed", f"{wind_speed} m/s") st.write(f"**Condition:** {description.capitalize()}") st.image(f"http://openweathermap.org/img/wn/{icon_code}@2x.png")
Vibe Coding Tip:
Streamlit provides many built-in components like st.columns()
for layout and st.metric()
for displaying key values. The AI is leveraging these to create a clean, organized interface.
The code should also include a loading spinner to show while fetching data:
# Search button if st.button("Get Weather"): if city: with st.spinner("Fetching weather data..."): weather_data = get_weather_data(city, api_key) if weather_data["cod"] != "404": display_weather_card(weather_data) else: st.error(f"City '{city}' not found. Please check the spelling and try again.")
Vibe Coding Tip:
The st.spinner()
function creates a loading animation while your app fetches data. This provides visual feedback to users that something is happening in the background.
Open the Composer (Ctrl/Cmd+K) and enter this prompt to add additional features:
I'd like to add more features to my weather app: 1. A 5-day forecast section 2. The ability to save favorite cities 3. Display the current date and time for the searched location 4. A map showing the location 5. Sunrise and sunset times
The generated code should include a function to fetch the 5-day forecast:
def get_forecast_data(city_name, api_key): base_url = "http://api.openweathermap.org/data/2.5/forecast?" complete_url = f"{base_url}q={city_name}&appid={api_key}&units=metric" response = requests.get(complete_url) return response.json()
Vibe Coding Tip:
This function is similar to the one for current weather, but it uses a different API endpoint (/forecast
) to get the 5-day forecast data.
The code should also include a function to display the forecast data:
def display_forecast(forecast_data): st.subheader("5-Day Forecast") # Create columns for each day cols = st.columns(5) # Process and display forecast for next 5 days for i, day_data in enumerate(forecast_data["list"][::8][:5]): date = datetime.fromtimestamp(day_data["dt"]).strftime("%a") temp = day_data["main"]["temp"] icon = day_data["weather"][0]["icon"] with cols[i]: st.write(f"**{date}**") st.image(f"http://openweathermap.org/img/wn/{icon}@2x.png") st.write(f"{temp:.1f}°C")
Vibe Coding Tip:
This function creates a row of columns, one for each day of the forecast. The [::8][:5]
syntax selects every 8th item from the forecast data (which gives us one reading per day) and limits it to 5 days.
The main code should be updated to fetch and display the forecast data:
# Search button if st.button("Get Weather") and city: with st.spinner("Fetching weather data..."): weather_data = get_weather_data(city, api_key) if weather_data["cod"] != "404": st.session_state.last_city = city display_weather_card(weather_data) # Get and display forecast forecast_data = get_forecast_data(city, api_key) display_forecast(forecast_data) # Display sunrise and sunset times sunrise = datetime.fromtimestamp(weather_data["sys"]["sunrise"]).strftime("%H:%M") sunset = datetime.fromtimestamp(weather_data["sys"]["sunset"]).strftime("%H:%M") st.subheader("Additional Information") col1, col2 = st.columns(2) with col1: st.write(f"**Sunrise:** {sunrise}") with col2: st.write(f"**Sunset:** {sunset}") else: st.error(f"City '{city}' not found. Please check the spelling and try again.")
Open the Composer (Ctrl/Cmd+K) and enter this prompt to improve error handling and user experience:
I want to improve the error handling and user experience of my weather app: 1. Add clear error messages when a city isn't found 2. Add a search button in addition to the text input 3. Remember the last searched city using session state 4. Add a loading animation while fetching data 5. Add a footer with credits and information
The generated code should include session state to remember the last searched city:
# Initialize session state for last city if 'last_city' not in st.session_state: st.session_state.last_city = "" # Input for city name with default value from session state city = st.text_input("Enter city name:", value=st.session_state.last_city)
Vibe Coding Tip:
Streamlit's session state allows you to store and retrieve values between reruns of your app. This is useful for remembering user inputs and preferences.
The code should include better error handling for various scenarios:
# Search button if st.button("Get Weather") and city: with st.spinner("Fetching weather data..."): try: weather_data = get_weather_data(city, api_key) if weather_data["cod"] == 200: st.session_state.last_city = city display_weather_card(weather_data) # Get and display forecast forecast_data = get_forecast_data(city, api_key) if forecast_data["cod"] == "200": display_forecast(forecast_data) else: st.warning("Forecast data is not available at the moment.") elif weather_data["cod"] == "404": st.error(f"City '{city}' not found. Please check the spelling and try again.") else: st.error(f"Error: {weather_data['message']}") except Exception as e: st.error(f"An error occurred: {str(e)}") st.info("Please check your internet connection and try again.")
Vibe Coding Tip:
Good error handling improves user experience by providing clear feedback when something goes wrong. The try-except
block catches any unexpected errors, while the conditional checks handle specific error cases.
Add a footer to the app with credits and information:
# Footer st.markdown("---") st.markdown( """""", unsafe_allow_html=True )Weather data provided by OpenWeatherMap
Created with Streamlit and Cursor AI
Make sure to save your app.py
file with all the code you've generated and modified.
Open the Composer (Ctrl/Cmd+K) and enter this prompt:
How do I run my Streamlit app to test it? Please provide the command and any necessary setup instructions.
Open a terminal in Cursor (Terminal > New Terminal) and run the following command to install the required packages:
pip install streamlit requests
In the terminal, run the following command to start your app:
streamlit run app.py
Vibe Coding Tip:
This command starts a local web server and opens your app in a browser. You can make changes to your code and the app will automatically reload to show the updates.
Test your weather app by:
Open the Composer (Ctrl/Cmd+K) and enter this prompt to customize the appearance:
I'd like to customize the appearance of my weather app: 1. Add a custom color theme 2. Improve the layout for mobile devices 3. Add animations for weather conditions 4. Create a dark/light mode toggle 5. Add custom CSS for better styling
The generated code should include custom CSS to improve the appearance:
# Custom CSS st.markdown(""" """, unsafe_allow_html=True)
Vibe Coding Tip:
Streamlit allows you to inject custom CSS using the st.markdown()
function with unsafe_allow_html=True
. This gives you more control over the appearance of your app.
The code might include a dark/light mode toggle:
# Initialize session state for theme if 'dark_mode' not in st.session_state: st.session_state.dark_mode = False # Theme toggle in sidebar with st.sidebar: st.title("Settings") if st.checkbox("Dark Mode", value=st.session_state.dark_mode): st.session_state.dark_mode = True theme = "dark" else: st.session_state.dark_mode = False theme = "light" # Apply theme if theme == "dark": st.markdown(""" """, unsafe_allow_html=True) else: st.markdown(""" """, unsafe_allow_html=True)
Run your app again to test the customizations:
streamlit run app.py
Make any additional adjustments to the styling as needed.
Open the Composer (Ctrl/Cmd+K) and enter this prompt:
How can I deploy my Streamlit weather app so others can use it? Please provide options and basic instructions.
Create a new file called requirements.txt
in your project folder with the following content:
streamlit requests
Vibe Coding Tip:
The requirements.txt
file lists all the Python packages your app needs to run. Deployment platforms use this file to install the necessary dependencies.
For a simple deployment using Streamlit Cloud:
Vibe Coding Tip:
Streamlit Cloud is a free hosting service specifically designed for Streamlit apps. It's the easiest way to deploy your weather app and share it with others.
Other deployment options include:
Once you've completed the basic weather app, consider these enhancements:
Add notifications for severe weather conditions in the searched location.
Implement automatic detection of the user's location for instant weather updates.
Add charts and graphs showing historical weather patterns for the selected location.
Allow users to compare weather conditions across multiple cities simultaneously.
Integrate with an air quality API to provide pollution data alongside weather information.
Suggest clothing, activities, or precautions based on current and forecasted weather.