#100DaysOfCode Day 5: More CRUD with Vim and Marlon Brando

Richard Russell
Cold Brew Code
Published in
6 min readMay 9, 2020

--

Today I will be continuing my application programming interface. More specifically, I will be adding the proper CRUD methods to the endpoints so that the database can also be updated/deleted.

`Probably the most masculine picture online. Notice the self-edge denim.

Changing Vim’s Color

Since I will be using Vim as my code editor of choice, I have decided to try and modify the editor towards my liking. Since most text-editors have number lines instead of the weird ~ that Vim uses, I used the command :set number to show these number lines. Also, I find that the default syntax color scheme to be quite uncomfortable to look at, especially with a few of the text being dark blue while my Terminal’s background is black. To solve this, I changed the color scheme to Murphy by using the command :colo murphy.

Their use of blood-red for comments is sexy

Adding a Movie list to the API

Recall that our code yesterday looks like the following:

from flask import Flask
app = Flask(__name__)
@app.route('/')
def hello():
return{'hello': 'world'}
app.run()

With a few changes, the new code looks like the following:

from Flask import Flask, jsonifymovies = [
{
"name": "Fight Club",
"cast": ["Brad Pitt", "Edward Norton", "Helena Bonham Carter", "Meat Loaf"],
"genre": ["Thriller"]
},
{
"name": "The Godfather",
"cast": ["Marlon Brando", "Al Pacino", "James Caan", "Diane Keaton"],
"genre": ["Crime", "Drama"]
}
]
app = Flask(__name__)@app.route('/movies')
def hello():
return jsonify(movies)
app.run()

From the code above, we can see a few changes. First, we have imported a new class from the flask package: jsonify. This class will be used to convert the movies list — which is also a new addition to the code — into a JSON file. Recall that a JSON file is basically a data file that can be read by the website. Also, we have rerouted the app.route() into /movies, meaning that the new path for the endpoint will have to be localhost:5000/movies.

The result of writing the movies list

However, I do find interesting here is that the output is not arranged in the same way as I wrote my source code. Here is a comparison picture:

Notice the difference between the order of each element

I infer that this might depend on the type of data or the length of the data. It might have given the highest priority to the longest array, with the lowest priority being a single variable. Will need more research on this.

Mr. Postman

I will be using Postman to test the API with different HTTP methods (recall the POST, PUT, GET, DELETE methods I wrote in the previous page. These methods can also be called CRUD).

Using Postman, open a new tab, and use the GET method to request the movie data from the server. Don’t forget to use the proper path /movies. After sending the GET request, Postman displayed the proper data:

Of course, in the name of good practice, I created a branch in GitHub during one of my Pomodoro break times and committed a branch:

After confirming that the GET request can be sent and a response is received, we can add other PAI endpoints for the CRUD function. To do so, add the following code above app.run():

@app.route('/movies', methods=[POST])
def add_movie():
movie = request.get_json()
movies.append(movie)
return {'id': len(movies)}, 200

These new lines of code will add the POST method to the API, meaning that a developer can add new data to the movie list. Going line-by-line, @app.route('/movies', methods=[POST]) essentially gives permission to post a new data set to the /movies path.

def add_movie(): represents the definition of a new function. However, what I am quite confused about is how they structure the function. Is it already the appropriate practice to write the function of the method below the @app.route() function? To me, I feel that the code will make more sense if there is whitespace before the start of defining a function. That way, the reader can know that a certain function is part of a certain method.

movie = request.get_json() is a function that will parse the data into a JSON file. movies.append(movie) basically means that the parsed movie file that is already in a JSON format will be added to the movies list. Note, append is a method used to add a new element into an array (Thank you, Codecademy). Finally, the function will return the number of elements that is in the movies list, as well as a 200 code — meaning that the method was successful.

@app.route('/movies/<int:index>', methods=['PUT'])
def update_movie(index):
movie = request.get_json()
movie[index] = movie
return jsonify(movie[index]), 200

The code above is used to define the PUT method. Because a PUT method will modify an element of the list, the path will need to specify the index of the element that will be modified, hence the route is @app.route('/movies/<int:index>', methods=['PUT']). The <int:index> the part is vitally important, as the index will be used to fill the function’s parameter, and then replacing the old element with the new one.

I find this part quite interesting because it shows that there isn’t any modification happening within the database. Instead, what’s happening is that one element will get overwritten by the new input produced by the developer. This can clearly be seen from the movies[index] = movie part of the code. Let me elaborate:

Assume that the element of movies[3] is the following:

{
"name": "A Streetcar Named Desire",
"casts": ["Marlon Brando", "Vivien Leigh", "Kim Hunter"],
"genre": ["Drama"]
}

Now, assume that the developer has recently watched a new Marlon Brando film and would like to replace the spot of A Streetcar Named Desire for On the waterfront. To replace the element, the developer would have to send a PUT method with the following input:

{
"name": "On the Waterfront",
"casts": ["Marlon Brando", "Eva Marie Saint", "Karl Malden"],
"genre": ["Drama", "Black and White"]
}

After sending the PUT method with the above as an input, the computer will automatically replace the whole element. I find this quite surprising because when I read that a PUT method will “update” the element, I thought the computer will intelligently detect which part of the data stays the same and which part is different. Apparently, updating actually means replacing.

@app.route('/movies/<int:index>', methods=['DELETE'])
def delete_movie(index):
movies.pop(index)
return 'None', 200

Similar to the PUT method, the DELETE method will need an index of its own, as it will only delete one element from the array. Using the pop method, an element can be deleted.

Wrap Up

I didn’t really get much done in today’s coding. However, what’s important is that I stay persistent in this challenge!

And as always, stay consistent.

--

--

Richard Russell
Cold Brew Code

i like to write about code. i also like cold brew coffee.