Delving Developer

Building a Movie Search App in React for Beginners

Eddie Cunningham
Eddie Cunningham
7 min readReact.js
Cover Image for Building a Movie Search App in React for Beginners

React is one of the most popular front-end libraries for building web applications. In this article, we'll walk you through how to build a movie search app in React from scratch. This tutorial is designed for beginners who want to learn the basics of React and API consumption.

Prerequisites

To get started with this tutorial, you'll need:

  • Basic knowledge of HTML, CSS, and JavaScript.
  • A text editor or an integrated development environment (IDE) like Visual Studio Code.
  • Node.js installed on your computer. You can download the latest version from the official website.
  • A free OMDB API key (you can get one here)

Project Setup

Let's start by creating a new React project using Create React App. Open your terminal and run the following command:

npx create-react-app movie-search-app

This command will create a new React project called movie-search-app and install all the necessary dependencies.

Folder Structure

Next, let's create a folder structure for our project. Create a new folder called src in the root directory of your project. Inside the src folder, create three new folders called components, pages, and utils.

  • The components folder will contain all the reusable React components that we'll use throughout our app.
  • The pages folder will contain the main screens of our app, such as the home page and search results page.
  • The utils folder will contain any utility functions or reusable logic that we'll use throughout our app.

Your project structure should look like this:

movie-search-app/
├── node_modules/
├── public/
│   ├── favicon.ico
│   ├── index.html
│   └── manifest.json
├── src/
│   ├── components/
│   ├── pages/
│   └── utils/
│   ├── App.css
│   ├── App.js
│   ├── App.test.js
│   ├── index.css
│   ├── index.js
│   └── logo.svg
├── .gitignore
├── package.json
├── README.md
└── yarn.lock

API Key

Now that we have set up our project, let's get an API key from the OMDB API for movie data. To get an API key, go to the OMDB API website and follow the instructions to get a free API key.

Home Page

Let's start building the home page of our movie search app. Inside the pages folder, create a new file called Home.js.

import React from 'react';

function Home() {
  return (
    <div>
      <h1>Movie Search App</h1>
      <p>Search for your favorite movies and TV shows!</p>
    </div>
  );
}

export default Home;

This is a simple React functional component that will render the home page of our app. We're displaying a heading and a short description to welcome users to our app.

Now let's create a new file called App.js in the root of src. We'll use this file to import and render our Home component.

import React from 'react';
import Home from './pages/Home';

function App() {
  return (
    <div>
      <Home />
    </div>
  );
}

export default App;

This is the main component of our app. We're importing and rendering the Home component inside our App component.

Fetching Movie Data

Now let's create a new file called MovieList.js inside the components folder. This component will display a list of movies based on the user's search query.

import React, { useState, useEffect } from 'react';

function MovieList({ searchQuery }) {
  const [movies, setMovies] = useState([]);

  useEffect(() => {
    fetch(`http://www.omdbapi.com/?apikey=YOUR_API_KEY&s=${searchQuery}`)
      .then(response => response.json())
      .then(data => setMovies(data.Search));
  }, [searchQuery]);

  return (
    <div>
      {movies.map(movie => (
        <div key={movie.imdbID}>
          <h2>{movie.Title}</h2>
          <p>{movie.Year}</p>
          <img src={movie.Poster} alt={`${movie.Title} Poster`} />
        </div>
      ))}
    </div>
  );
}

export default MovieList;

The MovieList component takes a searchQuery prop, which is the user's search query. We're using the useState hook to keep track of the movies returned by the API and the useEffect hook to fetch the movie data when the searchQuery prop changes.

We're using the fetch API to make a request to the OMDB API endpoint and passing in the searchQuery as a URL parameter. Once we receive the data, we're updating the state using the setMovies function.

Finally, we're rendering a list of movies by iterating over the movies state using the map function and displaying each movie's title, year, and poster.

Search Form

Next, let's create a search form component that will allow users to search for movies. Create a new file called SearchForm.js inside the components folder.

import React, { useState } from 'react';

function SearchForm({ handleSearch }) {
  const [searchValue, setSearchValue] = useState('');

  function handleSubmit(event) {
    event.preventDefault();
    handleSearch(searchValue);
  }

  return (
    <form onSubmit={handleSubmit}>
      <input
        type="text"
        placeholder="Search for a movie or TV show..."
        value={searchValue}
        onChange={(event) => setSearchValue(event.target.value)}
      />
      <button type="submit">Search</button>
    </form>
  );
}

export default SearchForm;

The SearchForm component takes a handleSearch prop, which is a function that will be called when the user submits the form. We're using the useState hook to keep track of the search query that the user enters in the input field.

When the user submits the form, we're handling the form submission by calling the handleSubmit function. We're preventing the default form submission behavior using the preventDefault method and calling the handleSearch function, passing in the searchValue state as an argument.

Finally, we're rendering a simple search form with an input field, a submit button, and some placeholder text.

Search Results Page

Now that we have the components to fetch movie data and search for movies, let's create a search results page that will display the search results. Create a new file called SearchResults.js inside the pages folder.

import React, { useState } from 'react';
import SearchForm from '../components/SearchForm';
import MovieList from '../components/MovieList';

function SearchResults() {
  const [searchQuery, setSearchQuery] = useState('');

  function handleSearch(searchValue) {
    setSearchQuery(searchValue);
  }

  return (
    <div>
      <SearchForm handleSearch={handleSearch} />
      <MovieList searchQuery={searchQuery} />
    </div>
  );
}

export default SearchResults;

The SearchResults component is rendering the SearchForm and MovieList components that we created earlier. We're using the useState hook to keep track of the search query entered by the user, and we're passing the searchQuery state as a prop to the MovieList component.

We're also passing a handleSearch function as a prop to the SearchForm component, which will be called when the user submits the form.

Routing

Now that we have the home page and search results page components, let's add routing to our app. We'll use the react-router-dom package to manage routing in our app.

First, let's install the react-router-dom package by running the following command in your terminal:

npm install react-router-dom

Next, let's import and use the BrowserRouter and Route components from the react-router-dom package inside our App component.

import React from 'react';
import { BrowserRouter, Route } from 'react-router-dom';
import Home from './pages/Home';
import SearchResults from './pages/SearchResults';

function App() {
  return (
    <BrowserRouter>
      <div>
        <Route exact path="/" component={Home} />
        <Route path="/search" component={SearchResults} />
      </div>
    </BrowserRouter>
  );
}

export default App;

We're wrapping our entire app in the BrowserRouter component and using the Route component to define our app's routing. We're defining two routes: one for the home page ("/") and one for the search results page ("/search"").

Styling

Finally, let's add some styling to our app to make it look more visually appealing. Create a new file called App.css in the src folder and add the following styles:

body {
  font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
  background-color: #262626;
  color: #fff;
  margin: 0;
}

.container {
  max-width: 900px;
  margin: 0 auto;
  padding: 20px;
}

h1 {
  font-size: 48px;
  font-weight: normal;
  margin-bottom: 20px;
}

p {
  font-size: 24px;
  margin-bottom: 20px;
}

form {
  display: flex;
  margin-bottom: 20px;
}

input[type="text"] {
  flex: 1;
  padding: 10px;
  font-size: 20px;
  border: none;
  border-radius: 5px 0 0 5px;
}

button[type="submit"] {
  padding: 10px 20px;
  font-size: 20px;
  border: none;
  border-radius: 0 5px 5px 0;
  background-color: #ff2e63;
  color: #fff;
  cursor: pointer;
  transition: background-color 0.2s ease-in-out;
}

button[type="submit"]:hover {
  background-color: #e6005c;
}

img {
  max-width: 100%;
  height: auto;
  margin-bottom: 20px;
}

We're adding styles to our app using CSS. We're setting the font family, background color, and text color for the entire body of our app. We're also adding styles for specific components like the header, search form, and movie list.

Conclusion

In this article, we covered the basics of building a movie search app in React. We started by creating a new React project using Create React App, added components to fetch movie data and search for movies, and implemented routing to navigate between the home page and search results page.

We also added some basic styles to make our app look more visually appealing. With these skills, you're ready to take on more complex React projects and explore different APIs to build dynamic web applications.