5. Progressive Web Apps (PWAs)
- PWA
- Progressive Web Apps (PWAs) are web applications that load like regular web pages or websites but can offer the user functionality such as working offline, push notifications, and device hardware access traditionally available only to native mobile applications.
- manifest
- Progressive Web Apps require a manifest which is a JSON file that contains information about how your app should appear when installed on a mobile device.
- icons
- App icons are crucial for branding. It is the first thing a user interacts with, even before launching your app. On mobile devices, icons are placed on the home screen. A quality graphic for the icon adds to users’ intuition to tap open the application. In PWA' (Progressive Web Apps)'s, the icons are configurable in the manifest file. Read more about app icons: How to Define App Icons.
Add the manifest and icons to your TV Maze Assignment:
- Rename the main html file
index.html
if it isn't already. - Get an icon: You'll need icons for different screen sizes. Two key sizes are 192x192 and 512x512 pixels, but others can be used as well. Create your own 512x512 icon or go to FlatIcon.
- Generate icons of different sizes: Upload your 512x512 icon to App Icon Generator to generate icons of different sizes. Once you download the zip file, only use the icons in the Android folder. The icons in the Apple and Windows 11 folders are overkill
- Create an icons folder: Place these icons in your app's icons directory and the manifest in the root directory (same directory as index.html).
- Generate a manifest: Use a website like PWA Manifest Generator to generate a manifest and a maskable icons.
- Update the location of the icon in the manifest. Add "icons/" in front of all the icon names in the manifest, otherwise it won't be able to find your icons. For a full explanation of the manifest file: https://pwa-workshop.js.org/1-manifest/.
- Add the rest of your icons to the manifest. Open the manifest in VSCode. Copy the code for the 512x512 icon, and make a new entry for each of your icons in the icons folder.
- Screenshots are required to be added to the manifest. Here are the rules:
- Width and height must be at least 320px and at most 3,840px
- The maximum dimension can't be more than 2.3 times as long as the minimum dimension
- At least once form factor must be wide (ex 1280x720)
- Only JPEG and PNG image formats are supported
- Chrome will display up to eight screenshots
- Typical form factors are 1280x720 and 720x1280
"screenshots":
{ "src": "screenshots/screenshot1.png", "sizes": "1280x720", "type": "image/png", "form_factor": "wide", "purpose": "any" }, { "src": "screenshots/screenshot2.png", "sizes": "720x1280", "type": "image/png", "purpose": "any" }
- Add the manifest to your base HTML template by putting the tag
link rel="manifest" href="manifest.json"
into the head. - Run your app using a local server in VS Code. You will need to install the extensions called "Live Preview" from Microsoft.
- Test if your manifest is working. You can check that the manifest is retrieved correctly by looking in the Applications tab of Chrome Developer Tools. The list of manifest properties, the screenshots, and the icons should be displayed. There should be no errors or warnings.
PWAs require a secure context (HTTPS) to be installable. This means you must host your PWA on a service that provides HTTPs (vs HTTP). Github offers this service for free.
Here's how you can host a website on GitHub using only GitHub’s web interface:
Step 1: Create a GitHub Repository
- Log in to your GitHub account (or sign up if you don’t have one).
- Create a new repository:
- Click the "+" icon in the top-right corner of the GitHub dashboard and select New Repository.
- Give the repository a simple, but meaningful name like:
tvmaze1
. - Choose Public (so GitHub Pages can serve it).
- Do not initialize the repository with a README (you’ll add files in the next step).
- Click Create repository.
Step 2: Upload Your Website Files to GitHub
- Open your Javascript file and change all your
http
tohttps
. PWA's only allow secure connections. - Navigate to the repository you just created.
- Click on the Add file button, then select Upload files.
- Drag and drop your website files (HTML, CSS, JavaScript, etc.) into the upload box.
- At minimum, you’ll need an
index.html
file, which will serve as the main page of your website. - Note: You will need to update your manifest `Start-URL` to be the name of your Github project followed by a forward slash
username.github.io/
ortvmaze1/
- At minimum, you’ll need an
- After you’ve uploaded your files, scroll down and click the Commit changes button. This will save the files to your repository.
Step 3: Enable GitHub Pages
- In the repository, go to the Settings tab at the top of the page.
- On the left-hand sidebar, click on the Pages section (it may be located near the bottom).
- Under the Source section, select "Deploy from a Branch".
- Under Branch, choose the branch that contains your website files (probably
main
). Leave the folder as/ (root)
if your website files are in the root of the repository. - Click Save.
Step 4: Visit Your Published Website
- Once GitHub finishes processing your site (this usually takes a minute or two), you’ll see a message at the top of the Pages section that shows the URL where your site is hosted.
- The URL will typically look like:
https://username.github.io/
orhttps://username.github.io/tvmaze1
.
- The URL will typically look like:
- Click the link to view your live website!
Step 5: Update Your Website
- Anytime you want to make changes to your website, you can return to the repository and either:
- upload new files through the Add file -> Upload files option.
- OR make the changes directly on Github
- GitHub Pages will automatically update your site with the new content once you commit your changes. These changes can take up to 10 minutes to show up. Therefore, you may want to test locally using Live Server, and just update on Github once in a while.
That's it! Your website is now hosted on GitHub Pages, and you can manage everything directly through GitHub's web interface.
- Use this service worker code. Save it as
sw.js
in the root of the scope you used in the manifest (likely the same folder as your index.html) It precaches files and fetches to the API that have been made. - In the service worker, modify
cache.addAll
to include all the files you want cached for offline use. Include your css, html, js, and any images that are a key part of your design. - Add a code block to your base js file to load the service worker. It should be something like
// load the service worker if ('serviceWorker' in navigator) { window.addEventListener('load', function() { navigator.serviceWorker.register('sw.js').then(function(registration) { console.log('Service Worker registered with scope:', registration.scope); }, function(error) { console.log('Service Worker registration failed:', error); }); }); }
- Confirm that your Service Worker is working. Run your website from local host, or on Github, open the Chrome Web Dev Tools > Application > Service Workers.
If it is working it should look like this:
If it is not working, you probably referenced a file incache.addAll
that doesn't exist.
The Service Worker you were given in earlier should cache all your code files, and images that are part of your interface. This allows your app to be loaded offline. In addition, it should also cache any fetches made by the app while it is online. What this means is if the app is being used offline, and a fetch is made that was cached, then it will load the data from that fetch and appear like it is working.
- Follow these instructions Service Workers - Caching Fetch Events to make your TV Maze app cache fetch events
- To test if your fetch events are being cached, look at Chrome Web Dev Tools > Application > Cache Storage, expand the menu, and see what is being cached. If fetches are being cached, test your app by going offline and repeating the same searches. Your app should work beautifully.
- Now add some code to display a message so that if a fetch is made that is not cached while the app is offline, says the app needs to be online to perform that action.
- To prompt the user to install your PWA, listen for the
beforeinstallprompt
event. - This event is triggered when the app meets installability criteria (like having a valid manifest and service worker).
- Copy the code below into your
script.js
file to handle the install prompt:// handle install prompt let deferredPrompt; window.addEventListener('beforeinstallprompt', (e) => { e.preventDefault(); deferredPrompt = e; const installButton = document.getElementById('installButton'); installButton.style.display = 'block'; installButton.addEventListener('click', () => { installButton.style.display = 'none'; deferredPrompt.prompt(); deferredPrompt.userChoice.then((choiceResult) => { if (choiceResult.outcome === 'accepted') { console.log('User accepted the install prompt'); } else { console.log('User dismissed the install prompt'); } deferredPrompt = null; }); }); });
- Add an install button in your HTML where users can click to install the PWA. This will be shown when
beforeinstallprompt
is run by the service worker.
How to Use Lighthouse in Chrome DevTools to Evaluate a PWA
Lighthouse is a powerful, automated tool available in Chrome DevTools that helps evaluate the quality and performance of Progressive Web Applications (PWAs). It generates detailed reports on various aspects like performance, accessibility, SEO, and adherence to PWA standards.
Why Use Lighthouse?
Evaluate PWA Compliance
Lighthouse checks if your app meets core PWA requirements, such as being installable, fast, and working offline.Improve User Experience
By identifying performance bottlenecks and accessibility issues, Lighthouse helps you build apps that work seamlessly for users.Optimize for SEO
It provides SEO insights to ensure your app is discoverable on search engines.Measure Performance
Lighthouse evaluates page load times, responsiveness, and other key metrics to help you create a faster application.Maintain Accessibility Standards
It highlights accessibility improvements for users relying on assistive technologies.
How to Run a Lighthouse Audit
Open Chrome DevTools
- Open your PWA in Chrome.
- Right-click on the page and select Inspect, or press
Ctrl+Shift+I
(Windows/Linux) orCmd+Opt+I
(Mac).
Navigate to the Lighthouse Tab
- In the DevTools panel, click on the Lighthouse tab. If it’s not visible, click the
>>
menu to reveal hidden tabs.
- In the DevTools panel, click on the Lighthouse tab. If it’s not visible, click the
Configure Audit Settings
- Select the type of audit you want to perform:
- Performance
- Accessibility
- Best Practices
- SEO
- Progressive Web App
(Tip: For a PWA evaluation, ensure "Progressive Web App" is checked.)
- Choose the Device type:
- Mobile: Simulates a low-end mobile device with slower network conditions.
- Desktop: Tests under desktop-specific conditions.
- Select the type of audit you want to perform:
Run the Audit
- Click the Generate Report button. Lighthouse will simulate loading your app and evaluate it based on the selected criteria.
- The process may take a few seconds to complete.
Review the Report
- The report includes scores for each category (e.g., PWA, Performance).
- Check specific recommendations to fix issues:
- Service Worker: Ensure it’s properly configured to allow offline usage.
- Manifest File: Verify completeness (e.g., start_url, icons, display).
- Performance Optimizations: Address render-blocking resources or large JavaScript files.
Iterate and Improve
- Address the highlighted issues in your codebase.
- Re-run the audit to confirm improvements.
Best Practices for PWAs Using Lighthouse
Installable App
Ensure your app has a valid web app manifest and meets installation criteria.Fast and Reliable
Focus on optimizing load times, enabling caching with a service worker, and ensuring functionality even with poor connectivity.Responsive Design
Verify your app works well on both mobile and desktop environments.Accessible UI
Fix accessibility issues to ensure everyone can interact with your app.SEO Optimization
Include metadata and structured content for better discoverability.
Using Lighthouse is a critical step in ensuring your PWA meets high-quality standards, providing a seamless and reliable experience for users.
- Apply this to your TV Maze PWA so that all evaluations are in the green and all red triangles are minimized.
- Test in an incognito window, because the Chrome Extensions in the school really affect performance.
- Use Chrome DevTools to verify that your PWA is installable.
- Open DevTools (F12 or right-click -> Inspect), then go to the Application tab.
- Check under "Manifest" to see if the manifest is correctly detected.
- Check under "Service Workers" to ensure your service worker is active.
- You can also test installability by visiting your app on mobile, where you should see an "Add to Home Screen" option.
Will be assessed as part 2 of the TV Maze Assignment with the additional criteria:
PWA Criteria All Lighthouse Categories in the green. Manifest complete with no errors. Service Worker registers w/ no errors. Works offline. Caches previous fetches. 5 All criteria met 4 Most criteria met 1 -2 issues 3 Some criteria met 3-4 small issues 2 Multiple issues 4+ problems 1 Incomplete
All the instructions above are summarized here: How to Make A PWA
Research
Read the following article: 3 Rules of App Design.The Project
Write a Progressive Web App that uses the Open Trivia Database API and the Pexels API. Be creative in your app design and utilize the API to make an app that users will install and use over and over again. Code that is taken from tutorials or other sources other than yourself is clearly commented with a link to the source. If credit is claimed for code that is not yours, the project will not be accepted.
Here is a very "in development" game created using the Bored API: Ms. Wear's Bored API Game Example. This is not good enough to justify a final project, as it is too simple. However, it does demonstrate how to use the API data from the Bored API creatively. It is a much more interesting use of the data than just displaying the fetch response in the webpage.
Milestones
- Monday Jan 6/Tuesday Jan 7: Share your app idea (how will you use the API creatively) and get it approved by Ms. Wear.
- Thursday Jan 9: In the console, display all trivia questions fetched from a single API request AND show at least one question with all possible answers in the webpage.
- Monday Jan 13: Fetch a Pexels image for any trivia question displayed in the webpage and show the image in the webpage.
- Thursday Jan 16: Basic responsive layout implemented
- Monday Jan 20: Finish layout and styling
- Wednesday Jan 22: In class marking of PWA criteria and code criteria
- Friday Jan 24 (3 hour class): In class demonstration of Final App
Marking Rubric
Functionality and Complexity(/10)- The work you put in is justifiably worth 20% of your mark. You have written a significant amount of JavaScript, and responsive CSS/HTML on your own. Only code and functionality created by you will be assessed.
- Creative use of Trivia API data. Has actual original JS code that allows user interactions and creatively utilizes data from the API
- Success of images searches from Pexels API to display related images with most questions
- Is entertaining or useful enough that users will install it and use it repeatedly
- Works on a desktop/laptop and a mobile android device
- Works offline with previous fetches cached
- Robust (the user cannot cause it to crash) and Reliable (never crashes on its own and always works as expected)
10 8 6 4 < 4 All criteria met Most criteria met Some criteria met Multiple Issues Incomplete All criteria met 1 -2 issues 3-4 small issues and/or 1 big issue 4+ problems A static HTML/CSS website was submitted.Meets Progressive Web App Criteria (/5)
- Manifest is recognized and contains basic required info.
- No manifest errors or warnings
- Screenshots are successfully registered in manifest
- Manifest refers to multiple sizes of icons.
- Service worker identified without errors.
- HTML/CSS/JS files and key images are cached and load offline
- Caches previous fetches so these results can be loaded if the user goes offline.
- It is installable.
- Lighthouse Audit: all 4 criteria in the Green Zone with red triangles minimized
5 4 3 2 1 All criteria met Most criteria met Some criteria met Multiple Issues Incomplete All criteria met 1 -2 issues 3-4 small issues 4+ problems Minimal attempt to create PWA.Usability and Presentation (/5)
- easy to use
- applies principles of design
- Pexels images are display cohesively along with questions
- attractive design using colors, fonts, css positioning, css effects
- responsive design
- Appropriate icon used without breaking copyright.
- If uncached fetches are made offline, an error message explaining this is displayed within the app interface.
- Navigation is provided so the user never has to click "back" to return to home page
5 4 3 2 1 All criteria met Most criteria met Some criteria met Multiple Issues Incomplete All criteria met 1 -2 issues 3-4 small issues 4+ problems Minimal attempt to create attractive, responsive, usable design.Code (/5)
- HTML Validates
- CSS Validates
- There is only one CSS file
- There is only one JS file
- No JS Errors in console
- Practices separation of languages
- Code that is taken from tutorials or other sources other than yourself is clearly commented with a link to the source. If credit is claimed for code that is not yours, the project will not be accepted.
5 4 3 2 1 All criteria met Most criteria met Some criteria met Multiple issues Incomplete All criteria met 1 -2 issues 3-4 issues 4+ problems Not coded to standards taught in class.
You will create a JavaScript function that fetches image data from the Pexels API based on a search term. Follow these instructions step-by-step:
1. Understand the Code Components
- API URL: The URL to fetch data from the Pexels API. It requires a search term.
- Headers: API calls to Pexels require an authorization key to access their services.
- Fetch Function: Sends the request to the Pexels API and retrieves image data.
- Error Handling: Ensures your program handles errors gracefully if the API call fails.
2. Implement the Code
- Copy and paste the following code into your JavaScript file:
const url = "https://api.pexels.com/v1/search?per_page=1&query=" + search;
const headers = {
"Authorization": "b7BNU08kvp8NLPcOdymXHfoiCuXMIF6nNaYnZNtYIzjoWERPQglJ5w8z"
};
try {
const response = await fetch(url, { headers });
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const data = await response.json();
console.log(data);
return data;
} catch (error) {
console.error("Error fetching data:", error);
}
3. Add a Search Term
- Replace the
search
variable with an actual search term or create a function to accept user input. For example:
const search = "mountains"; // Example search term
4. Wrap the Code in a Function
- To make the code reusable, wrap it in an
async
function:
async function fetchPexelsData(search) {
const url = "https://api.pexels.com/v1/search?per_page=1&query=" + search;
const headers = {
"Authorization": "b7BNU08kvp8NLPcOdymXHfoiCuXMIF6nNaYnZNtYIzjoWERPQglJ5w8z"
};
try {
const response = await fetch(url, { headers });
if (!response.ok) {
throw new Error(`HTTP error! Status: ${response.status}`);
}
const data = await response.json();
console.log(data);
return data;
} catch (error) {
console.error("Error fetching data:", error);
}
}
5. Test Your Code
- Call the function with a search term and verify that it works:
fetchPexelsData("sunsets");
- Check the console for the returned data.
6. Experiment and Expand
- Try searching for different keywords.
- Use the
data
object to extract and display image details likesrc
oralt
text.
Notes:
- The authorization key in the code is for demonstration purposes. Replace it with your own API key obtained from Pexels API.
- Be careful not to share your API key publicly.
Ms. Wear's Example of Hidden API Keys and Preventing CORS errors on Glitch