Browser extensions - Popup weather extension

I'm a full-stack developer from South Africa 🇿🇦. I love writing about JavaScript, HTML and CSS.
Search for a command to run...

I'm a full-stack developer from South Africa 🇿🇦. I love writing about JavaScript, HTML and CSS.
No comments yet. Be the first to comment.
In this article, we'll be exploring how to add browser notifications to our browser extension. As the starting point, I'll use our popup extension. If you want to follow along, use the following GitHub repo. The result of this article is the followin...
Most of you know me for my consistency, a golden arrow in my blog series. I've written 1000 articles in 1008 days! Almost an article a day, and my honeymoon was the only holiday I ever took. I'm super proud of this achievement; it has been a fantasti...

It's not the first time I'll be talking about community. I think it's an essential aspect of any successful tool. This shows in my previous explorations of Astro, Medusa, and now Vendure as well. All these products thrive in a super open, welcoming, ...

The cool part about Vendure is how easy it is to set up and how abstract each layer is. Basically, we get the following elements: External database Server Worker Admin UI Frontend While this is amazing, it also brings a bit of complexity when it co...

The previous article looked at customizing Vendure on a data and process level. In this article, we'll look at customizing emails, as they are often a big part of a webshop system. We'll be looking at two different layers of customization for customi...

Even though Vendure is a pretty significant project out of the box, in some cases, we might want to go in and modify some elements to work to our specific use case. In this article, I'll take a high-level look at some elements we can customize within...

In the previous article, we created a new tab experience that could load the weather for our current location. This article will convert what we learned to make it work in a popup extension.
If you like to follow along, take the following branch as your starting point. (or read up on the article)
The first thing we'll want to do is create our Weather widget. This will be the main component that shows the current weather.
Create a new file called Weather.jsx inside your src directory.
Start by bootstrapping the React component like this.
export default function Weather() {
return (
<div>
<h2>The weather today ☁️</h2>
</div>
);
}
Let's open up our App.jsx file and load this component.
import Weather from './Weather';
export function App() {
return (
<div className='flex flex-col items-center justify-center w-screen h-screen bg-indigo-400 text-6xl font-bold text-white'>
<Weather />
</div>
);
}
We must first ensure access to some external API to load weather data. I'm using the OpenWeather API because it has a generous free tier.
Let me show you how you can get an API key from there.
First, head over to OpenWeather and signup. You get a massive free tier.
Once you are logged in, find the API key, as you'll need this in a bit.

Once you have the key, head back to your project and create a .env file at the root of your project.
Inside we'll place our API key and the URL to the API.
VITE_APP_API_URL='https://api.openweathermap.org/data/2.5'
VITE_APP_API_KEY='YOUR_API_KEY'
Note: You can see they are prefixed with
VITE_as we use Vite as our build tool.
Now let's head back over to the weather component and call the API so we can fetch the data.
The first thing we'll need is a state to store the lat/long for the user and a state that will store the actual data returned by the API.
const [latLng, setLatLng] = useState({});
const [data, setData] = useState(null);
Then we'll want to add a useEffect that will take care of retrieving the geolocation from the user and fetching the API. The completed call will look like this.
useEffect(() => {
if (!latLng.lat && !latLng.long) {
navigator.geolocation.getCurrentPosition(function (position) {
setLatLng({
lat: position.coords.latitude,
long: position.coords.longitude,
});
});
return;
}
if (!data) {
fetch(
`${import.meta.env.VITE_APP_API_URL}/weather/?lat=${latLng.lat}&lon=${
latLng.long
}&units=metric&APPID=${import.meta.env.VITE_APP_API_KEY}`
)
.then((res) => res.json())
.then((result) => setData(result));
}
}, [latLng]);
The last thing we want to change is to render the data in our view. I added a loading text in case our app still loads the data.
return (
<div>
<h2>The weather today ☁️</h2>
<br />
{!data ? (
<p>Loading...</p>
) : (
<>
<p>Weather for: {data.name}</p>
<p>
Temp: {data.main.temp}° ({data.weather[0].main})
</p>
</>
)}
</div>
);
And that's it. Our component is now ready to be used.
Create a new build and install the extension in developer mode.
If we now try to open the extension, you'll notice it's not loading!

And if you right-click the popup extension and choose Inspect, you'll see the developer tools popup.
In the console, you will see a message stating we didn't ask for the proper permissions for the geolocation.

Let's open our manifest.json and add the following permission line.
"permissions": ["geolocation"]
Now build and rerun your application. You should now be able to get your current location weather!

You can also see the complete code on this GitHub repo.
Thank you for reading my blog. Feel free to subscribe to my email newsletter and connect on Facebook or Twitter