Project setup
I have added this whole project to a public github repo and I have broken down each step as a commit so it should be easy to follow. This is just as an aid, we will be creating the project from scratch so there is no need to clone the code.
Let’s start with a fresh directory, I have named the project
tutorial-node-database
. Run the following to create the file structure.mkdir tutorial-node-database cd tutorial-node-database
touch knexfile.js touch index.js touch store.js
mkdir public touch public/index.html touch public/app.js
# choose all defaults when prompted npm init
We are using Knex with MySQL and creating a small API using express, so you need to install
knex
and express
. We’ll also use the body-parser
module.npm i knex mysql express body-parser --save
knex
should be installed globally alsonpm i knex -g
When creating a new project I like to add a minimal .gitignore file so that I can easily check everything in without including the
node_modules
folder or .DS_Store
files that MacOS likes to create.printf "node_modules\n.DS_Store" > .gitignore
Don’t worry if you don’t understand the bash code above. All it does is put
node_modules
followed by a newline \n
followed by .DS_Store
into a file called .gitignore
. It’s perfectly reasonable to use an editor to do this sort of thing if that’s more simple for you.HTTP API
We’ll start with a simple express app, serving the public directory, with a
/createUser
endpoint to write some data to the database.const express = require('express') const bodyParser = require('body-parser')
const store = require('./store')
const app = express()
app.use(express.static('public')
)
app.use(bodyParser.json())
app.post('/createUser', (req, res) => {
store
.createUser({
username: req.body.username,
password: req.body.password
})
.then(() => res.sendStatus(200))
})
app.listen(7555, () => { console.log('Server running on http://localhost:7555') })
Save this to
index.js
. When we run this file, the server will listen on http://localhost:7555 for POST requests to /createUser
and pass those requests to the store file. The server will then respond with a 200 status code (200 is the code that every HTTP server uses to say that the request was successful).
For the time being, we will mock the store in order to check that our API works.
module.exports = { createUser ({ username, password }) { console.log(`Add user ${username} with password ${password}`) return Promise.resolve() } }
Save this to
store.js
. Note that the addLog
function returns a promise so that you know when it is done. If the use of promises here is a little confusing, it might be worth checking out some Promise tutorials, they are an essential concept in modern Javascript.
Now, lets write a simple
index.html
, including app.js
. We add app.js
at the bottom of the HTML here rather than the head
so that we can easily query elements above the script, without needing to use something like jQuery.ready
or the DOMContentLoaded
event to wait for them to load.<!DOCTYPE html> <html> <head> <title>Node database tutorial</title> </head> <body> <form class="CreateUser"> <h1>Create a new user</h1> <input type="text" class="username" placeholder="username"> <input type="password" class="password" placeholder="password"> <input type="submit" value="Create user"> </form> <script src="/app.js"></script> </body> </html>
The
app.js
script should look like the below and will be used to hit the server’s /createUser
endpoint.const CreateUser = document.querySelector('.CreateUser') CreateUser.addEventListener('submit', (e) => { e.preventDefault() const username = CreateUser.querySelector('.username').value const password = CreateUser.querySelector('.password').value post('/createUser', { username, password }) })
function post (path, data) { return window.fetch(path, { method: 'POST', headers: { 'Accept': 'application/json', 'Content-Type': 'application/json' }, body: JSON.stringify(data) }) }
Save this to
public/app.js
and start your server.
0 Comments