A simple Ruby on Rails authentication API using devise-token-auth and PostgreSQL
Gems used for development:
- devise-token-auth for API authentication
- RSpec for tests/specs
- Rubocop for lint
- Rack-CORS for cross-origin resource sharing
To run the application, you need to install Ruby ~> 3.3.4 and Rails ~> 7.1.3, you'll also need to install PostgreSQL ~> 14
- Clone this repository to your local machine:
git clone [email protected]:zutin/simple-auth.git
- Navigate to the project directory:
cd simple-auth
- Install the project dependencies:
bundle install
- Create the database:
rails db:create
- Run the database migrations:
rails db:migrate
FYI: It is highly recommended to run the application tests using RSpec after installing so you can make sure everything is working fine.
- Start local server using another port:
rails server -p 4000
- Access the application at:
http://localhost:4000
You can run tests by navigating to the project folder:
cd simple-auth
And using RSpec to run all tests:
rspec
Attribute | Type |
---|---|
id | Integer |
provider | String |
uid | String |
String | |
created_at | Datetime |
updated_at | Datetime |
HTTP Request
- Header
Authorization: Bearer [access_token]
- Endpoint
http://localhost:4000/employees
Response - if authenticated
HTTP/1.0 200 OK
Content-Type: application/json
[
{
"id": 1,
"provider": "email",
"uid": "[email protected]",
"email": "[email protected]",
"created_at": "2024-08-01T18:20:32.383Z",
"updated_at": "2024-08-01T18:20:32.546Z"
}
]
Response - if not authenticated
HTTP/1.0 401 Unauthorized
Content-Type: application/json
{
"errors": [
"You need to sign in or sign up before continuing."
]
}
HTTP Request
- Body
{
"email": "[email protected]",
"password": "password"
}
- Endpoint
http://localhost:4000/auth/sign_in
Response - if it successfully logs in
- Headers
access-token: mzaWvXr3zMFpTTCOHTNIeQ
token-type: Bearer
client: tl3EhH7yIBTOO7MURHAEkA
uid: [email protected]
authorization: Bearer eyJhY2Nlc3MtdG9rZW4iOiJtemFXdlhyM3pNRnBUVENPSFROSWVRIiwidG9rZW4tdHlwZSI6IkJlYXJlciIsImNsaWVudCI6InRsM0VoSDd5SUJUT083TVVSSEFFa0EiLCJleHBpcnkiOiIxNzIzNzQ2MzU2IiwidWlkIjoidGVzdDFAdGVzdC5jb20ifQ==
- Body
HTTP/1.0 200 OK
Content-Type: application/json
{
"data": {
"email": "[email protected]",
"provider": "email",
"uid": "[email protected]",
"id": 1
}
}
Response - if it fails to log in
- Body
HTTP/1.0 401 Unauthorized
Content-Type: application/json
{
"success": false,
"errors": [
"Invalid login credentials. Please try again."
]
}
HTTP Request
- Headers
access-token: mzaWvXr3zMFpTTCOHTNIeQ
token-type: Bearer
client: tl3EhH7yIBTOO7MURHAEkA
uid: [email protected]
authorization: Bearer eyJhY2Nlc3MtdG9rZW4iOiJtemFXdlhyM3pNRnBUVENPSFROSWVRIiwidG9rZW4tdHlwZSI6IkJlYXJlciIsImNsaWVudCI6InRsM0VoSDd5SUJUT083TVVSSEFFa0EiLCJleHBpcnkiOiIxNzIzNzQ2MzU2IiwidWlkIjoidGVzdDFAdGVzdC5jb20ifQ==
- Endpoint
http://localhost:4000/auth/sign_out
Response - if it successfully signs out
- Body
HTTP/1.0 200 OK
Content-Type: application/json
{
"success": true
}
Response - if it fails to sign out
- Body
HTTP/1.0 404 Not Found
Content-Type: application/json
{
"success": false,
"errors": [
"User was not found or was not logged in."
]
}
HTTP Request
- Body
{
"email": "[email protected]",
"password": "password"
}
- Endpoint
http://localhost:4000/auth/sign_up
Response - if it successfully creates a new employee
- Headers
access-token: mzaWvXr3zMFpTTCOHTNIeQ
token-type: Bearer
client: tl3EhH7yIBTOO7MURHAEkA
uid: [email protected]
authorization: Bearer eyJhY2Nlc3MtdG9rZW4iOiJtemFXdlhyM3pNRnBUVENPSFROSWVRIiwidG9rZW4tdHlwZSI6IkJlYXJlciIsImNsaWVudCI6InRsM0VoSDd5SUJUT083TVVSSEFFa0EiLCJleHBpcnkiOiIxNzIzNzQ2MzU2IiwidWlkIjoidGVzdDFAdGVzdC5jb20ifQ==
- Body
HTTP/1.0 200 OK
Content-Type: application/json
{
"status": "success",
"data": {
"email": "[email protected]",
"provider": "email",
"uid": "[email protected]",
"id": 1,
"created_at": "2024-08-01T18:20:32.383Z",
"updated_at": "2024-08-01T18:20:32.546Z"
}
}
Response - if it fails to create a new employee
- Body
HTTP/1.0 422 Unprocessable Content
Content-Type: application/json
{
"status": "error",
"data": {
"id": null,
"provider": "email",
"uid": "",
"email": "[email protected]",
"created_at": null,
"updated_at": null
},
"errors": {
"email": [
"has already been taken"
],
"full_messages": [
"Email has already been taken"
]
}
}