SKILLS

Languages

python two snakes logoPython
C++ LogoC++

Go

JS LogoJavaScript
TS LogoTypeScript

Web Frameworks

react light blue atoms logoReact
Svelte LogoSvelte
Next.js
Flask LogoFlask icon by Icons8

Libraries

PyTorch, Pandas, NumPy, OpenCV, Selenium

SOCIAL

github whitelinkedin in logo

DateTemp

By Michael West

April 5, 2025


Try it out!

Code


Background

Have you ever walked outside after a long winter and it's suddenly 65 and sunny so you think that maybe winter is finally over, only for it to be 28 and snowing the next day? Yeah...me too, especially in Ann Arbor where I went to college. I got sick and tired of having false optimism about the end of winter and wanted to build a tool that was a litttlllleeee more reliable than good 'ole Punxsutawney Phil, so I decided to get data from the same day for the last 25 years to see if the current weather is the normal, or just an outlier.


Tech Stack

The primary motivator for building this app was getting more experience with developing backends and using databases, and linking them to the frontend. I've written REST APIs in both Python and Node.js before so I wanted to try something different, and since I'm currently learning Go, I figured this would be the perfect opportunity to learn by doing. I wrote the frontend in Next.js with TailwindCSS since I'm used to it and deploying on Vercel is super easy, and I deployed my backend on Google Cloud Platform since I've never used it and wanted to learn. I also spun up a simple PostgreSQL database using Supabase. Overall the structure of the project looks like this: Client Browser (TS webpage) -> Vercel Server running a TS API -> GCP Go Backend -> Open-Meteo API or Supabase SQL DB. Overall this stack gave me a good mix of being challenged with new services I've never worked with before while keeping the critical components familiar so I was able to develop at a reasonable pace.


Getting the Current Weather

First thing's first, I needed a way to get the current weather, as well as a rough hourly forecast. After doing some digging, I found the Open-Meteo Weather API which not only has current weather, but also historical records! To serve the current weather for a user my backend calls their current weather API, does some data formatting, and then serves it to the frontend.


Getting Historical Weather

My original goal was to have a database of all the historical records I would need, which would make backend calls faster and cut down significantly on the amount of external API calls I was making. However, I quickly realized that since I'm using free tiers of all the providers, I don't have anywhere near enough storage for that. I decided to just store the default location (Ann Arbor since I'm currently living here) historical records in the DB, giving me the ability to practice with a database and speeding up initial load times while still allowing users to get the weather history for any location. There's two kinds of tables in the DB: Hourly History and Daily History. Hourly History contains 24 individual hour entries of the weather per day for every day now-Jan. 1, 2000, and Daily contains one entry per day, giving data like the average temp., daily high, low, precipitation, etc. In order to load the historical browser, the backend grabs every record from the Hourly Table that matches Hour, Month and Day, and Latitude and Longitude. If the specificed location has no saved records in the DB, it instead fetches them from OpenMeteo, but due to API limitations has to perform one individual query per year (so 25 queries), which is quite slow. The better solution here would be having a larger database, but I'm limited by storage constraints so only Ann Arbor records are stored.


Lessons Learned

I learned a TON from this project, here are the five biggest things:

  1. Building a REST API in Go w/Gin: Building this project taught me a ton of syntax and best practices that I didn't know previously. I really like how easy it is to define structs in your JSON data's format, it made reading in API response data super easy.

  2. Database Design: I gained valuable experience designing and working with database schema, particularly deciding on optimal variable typing and managing RLS policies.

  3. Google Cloud Platform Deployment: While I've containerized apps before, I've never deployed to GCP. After deploying this project I have a much greater understanding of how powerful GCP is and basic project deployment principles.

  4. Server-Side API Routing: Using Next.js API routing, I was successfully able to query the Go API endpoints from the server-side only! I didn't know this practice existed before this project and it made me think more about the relationship between client-side and server-side and APIs.

  5. Frontend Loading Screens: Originally, changing locations would keep the page the same while it waited for the data in the background, and then update it. This was misleading and for very slow responses, could give false weather impressions. I learned the importance of visibly indicating outdated data and current fetching processes to the user.


Conclusion

Overall I had a great time builing this project! I definitely learned a LOT about deploying and managing a backend and using external database providers. I might build some more features into the app in the future, but most likely it will stay very similar to the current iteration, it's a very simple idea after all. Thanks for reading, and I hope you find it useful!