RESTful Node.js: A Structured Approach
  • Book Cover
  • About the Author
  • Links and Resources
  • Part I: The Why
    • Foreword
    • Preface
    • Chapter 1: Introduction
      • The Rise of REST and Distributed Systems
      • Problem #1: Structureless Design, Structureless REST
      • The Emergence of JavaScript and Node.js
      • Problem #2: Structureless JavaScript, Structureless Node.js
      • Behold, the Solution: A Structured Approach
      • Summary
  • Part 2: The Theory
    • Chapter 2: REST Origins
      • A Brief History of the Web and the Birth of REST
      • REST vs. HTTP
      • REST - The Abstract Web Architecture
      • HTTP - A Peak at REST's Concrete Implementation
      • What does it mean for an API to be RESTful?
      • Measuring "RESTfulness" with Richardson Maturity Model
      • Pragmatic REST vs Dogmatic REST
      • Summary
    • Chapter 3: RESTful API Design Guidelines and "Best Practices"
      • Theories vs. Principles vs. Guidelines
      • URI Design
      • Method Verbs
      • Status Codes
      • Representational Design
      • Metadata Design
      • Versioning Strategies
      • Security Considerations
      • Documentation
      • Case Study: GitHub
      • Summary
    • Chapter 4: Structured JavaScript Architecture
      • The Monstrous Monolith and Its Downfall
      • Layered/N-Tier Architecture: The Unpopular Proven Way
      • Microservices and Distributed Computing: A Popular Misdirection
      • Summary
    • Chapter 5: The 8 Step Recipe
      • Route Name (URI)
      • Input Request
      • Middleware
      • Validation
      • Domain
      • Events
      • Output Response
      • Test, Refactor, Document
      • Summary
  • Part 3: The Code
    • Chapter 6: Introduction to the Bookstore API
      • The Bookstore API Endpoint Specifications
      • API Design and Code Structure
      • Project Setup
      • Summary
    • Chapter 7: Retrieving Books from our API
      • Retrieving All Books - Planning
      • Retrieving All Books - Implementation
      • Retrieving A Book By ID - Planning
      • Retrieving A Book By ID - Implementation
      • Summary
    • Chapter 8: Adding Authentication to our API
      • Registering the User - Planning
      • Registering the User - Implementation
      • Logging the User In - Planning
      • Logging the User In - Implementation
      • Getting Authenticated User - Planning
      • Getting Authenticated User - Implementation
      • Summary
    • Chapter 9: Adding the Create, Update, and Delete Operations to our API
      • Creating A Book Listing - Planning
      • Creating A Book Listing - Implementation
      • Updating A Book Listing By ID - Planning
      • Updating A Book Listing By ID - Implementation
      • Deleting A Book Listing By ID - Planning
      • Deleting A Book Listing By ID - Implementation
      • Summary
    • Chapter 10: Testing our API
      • Testing the Request
      • Testing the Middleware
      • Testing the Validation
      • Testing the Domain
      • Testing the Event
      • Testing the Response
      • Testing the Controller
      • Integration Test
      • Summary
  • Conclusion
    • Final Words
  • Bonus!
    • Refactoring to HATEOAS
  • Appendix
    • Sources & References
Powered by GitBook
On this page
  • 1 - Route Name
  • 2 - Input Request
  • 3 - Middleware
  • 4 - Validation
  • 5 - Domain
  • 6 - Events
  • 7 - Response
Edit on GitHub
  1. Part 3: The Code
  2. Chapter 8: Adding Authentication to our API

Registering the User - Planning

PreviousChapter 8: Adding Authentication to our APINextRegistering the User - Implementation

Last updated 3 years ago

Refer back to section for the API endpoint specifications.

1 - Route Name

Following the guidelines in chapter 6, and , we will create the following URI. Since it is a resource creation, using POST over any other method verbs would make sense here.

As for the namespace, we will follow This means we should not use any verbs, but rather let the POST method verb speak for itself on what resource it will create. A lot of developers will make the mistake of making the URI something like this /api/v1/auth/regster or /api/v1/users/create. Don't do this as it is the exact opposite of the guideline we are trying to follow.

Also, don't forget to always pluralize the resources your endpoints. In our case, the resource being users.

The following URI is what we will be going with.

POST /api/v1/users

2 - Input Request

As stated from the endpoint specifications in the previous chapter, we will accept the following input fields from the client.

  • first_name

  • last_name

  • email

  • password

  • password_confirmation

  • phone_number

3 - Middleware

Since this is a going to be a public user registering for an account, no middleware is necessary.

However, since this chapter has a bunch of input validation, we'll be adding in a global middleware that will catch and handle all exceptions in our application. You will see more of this in the next section.

4 - Validation

From the looks of the specification, it would seem like we'll need to perform the following validation rules for each of the fields.

  • first_name - required.

  • last_name - required.

  • email - required, must be a valid email format.

  • password - required, at least 6 characters.

  • password_confirmation - required, password and password_confirmation must match.

  • phone_number - required, must be a valid phone number format.

5 - Domain

From the specifications, it looks like we will need the following user entity in our domain layer.

userModel

  • first_name

  • last_name

  • email

  • password

  • phone_number

We will also need some sort of way to make a query to the database to insert the user in, so we'll create a userRepository layer with the method createUser() to do so.

userRepository

  • createUser()

On top of that, our controller will call a service to registerUser(), in this case, it will be the authService which will use the userRepository layer. We'll also need to keep in mind that we will have to do some sort of database validation here since there can only be one unique email in the users table.

authService

  • registerUser()

This is a rough outline of how we are going to be implementing these functions, we'll take a deeper dive at the implementations in the next section of this chapter.

*Note: for the purposes of demonstration in this book, we will not be hashing our passwords. If you want to deploy any sort of authentication system into production, always remember to hash your passwords.

6 - Events

Send an email to the registered user's email letting them know that they have successfully registered.

7 - Response

There are 4 possible responses we could possibly return from this endpoint.

The first is a successful response in which we have successfully inserted the newly registered user into the database and fired off an email to that user.

{
    "status": "success",
    "code": 201,
    "message": "User has successfully been registered."
    "data": {
        "id": "61f889bbc6bbf81a97ba69d6",
        "first_name": "John",
        "last_name": "Doe",
        "email": "johndoe@email.com",
        "phone_number": "1234567890"
    },
    "errors": null
}

The second would be an error on an invalid input request payload.

{
  "status": "error",
  "code": 422,
  "message": "Input fields are of not the correct form.",
  "data": null,
  "errors": [
    "This DTO's property is required: email.",
    "This DTO's property is required: password.",
    "This DTO's property is required: password_confirmation.",
    "This DTO's property is required: phone_number."
  ]
}

*Note: I won't be mentioning any more DTO validations in the ensuing chapters as the response is quite routine for most API calls with an input request body. So for login user, create a book, and update a book API endpoints, it's implied that a DTO will yield a particular response depending on the input from the client.

The third would be an error on the form validation.

{
  "status": "error",
  "code": 400,
  "message": "There were errors with the validation.",
  "data": null,
  "errors": [
    "The email format is invalid.",
    "The password confirmation and password fields must match."
  ]
}

Lastly, the fourth would be a backend database validation checking if an email address is already taken.

{
  "status": "error",
  "code": 409,
  "message": "This email is already taken.",
  "data": null,
  "errors": ["This email is already taken."]
}
Method Verbs
URI Design
Guideline #4: Avoid actions and verbs in the URI in chapter 3, URI Design, URI Path Design.
Chapter 6, The Bookstore API Endpoint Specifications, API Endpoint #1: User Registration