Skip to content

Commit

Permalink
add:redis sample app (#80)
Browse files Browse the repository at this point in the history
  • Loading branch information
shivamsouravjha authored Oct 31, 2023
1 parent 81d4646 commit 5dcdf2b
Show file tree
Hide file tree
Showing 31 changed files with 1,495 additions and 0 deletions.
21 changes: 21 additions & 0 deletions gin-redis/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# If you prefer the allow list template instead of the deny list, see community template:
# https://github.com/github/gitignore/blob/main/community/Golang/Go.AllowList.gitignore
#
# Binaries for programs and plugins
*.exe
*.exe~
*.dll
*.so
*.dylib

# Test binary, built with `go test -c`
*.test

# Output of the go coverage tool, specifically when used with LiteIDE
*.out
*.env
# Dependency directories (remove the comment below to include it)
# vendor/

# Go workspace file
go.work
17 changes: 17 additions & 0 deletions gin-redis/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Use an official Golang runtime as a parent image
FROM golang:1.20

# Set the working directory inside the container
WORKDIR /app

# Copy the local package files to the container's workspace
COPY . .

# Build the Go application
RUN go build -o main .

# Expose port 3001
EXPOSE 3001

# Command to run the Go application
CMD ["./main"]
240 changes: 240 additions & 0 deletions gin-redis/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,240 @@
## Introduction

A sample user authentication to test Keploy integration capabilities using [Gin](https://gin-gonic.com/) and [Redis](https://redis.io/).

## Setup URL shortener

```bash
git clone https://github.com/keploy/samples-go.git && cd samples-go/gin-redis
go mod download
```

## Installation

There are two methods to run the sample application using Keploy :-

1. [Using Docker](#running-app-using-docker)
2. [Natively on Ubuntu/Windows(using WSL)](#run-app-natively-on-local-machine)

## Running app using Docker

Keploy can be used on Linux & Windows through [Docker](https://docs.docker.com/engine/install/), and on MacOS by the help of [Colima](https://docs.keploy/io/server/macos/installation)


### Create Keploy Alias

We need create an alias for Keploy:
```bash
alias keploy='sudo docker run --pull always --name keploy-v2 -p 16789:16789 --privileged --pid=host -it -v "$(pwd)":/files -v /sys/fs/cgroup:/sys/fs/cgroup -v /sys/kernel/debug:/sys/kernel/debug -v /sys/fs/bpf:/sys/fs/bpf -v /var/run/docker.sock:/var/run/docker.sock -v '"$HOME"'/.keploy-config:/root/.keploy-config -v '"$HOME"'/keploy-config:/root/keploy-config --rm ghcr.io/keploy/keploy'
```

> **Since, we are on the docker image the Redis URL will be myredis:6379 instead of localhost:6379. This needs to be updated in `helpers/redis/redisConnect.go` file**
### Create a Docker network
```
sudo docker network create <networkName>
```

### Let's start the Redis Instance
Using the docker-compose file we will start our Redis instance:-
```bash
sudo docker run -p 6379:6379 -d --network <networkName> --name myredis redis
```
```bash
docker build -t gin-app:1.0 .
```

### Capture the Testcases

```shell
keploy record -c "docker run -p 3001:3001 --name RediApp --network <networkName> --name ginRedisApp gin-app:1.0"
```

To genereate testcases we just need to make some API calls. You can use [Postman](https://www.postman.com/), [Hoppscotch](https://hoppscotch.io/), or simply `curl`

### 1. Request OTP

```bash
curl --location 'localhost:3001/api/[email protected]&username=shivamsourav'
```

this will return the OTP response.
```
{
"status": "true",
"message": "OTP Generated successfully",
"otp": "5486"
}
```

**2. Verify OTP**

```bash
curl --location 'localhost:3001/api/verifyCode' \
--header 'Content-Type: application/json' \
--data-raw '{
"otp":2121,
"email":"[email protected]"
}'
```
this will return the OTP verification response.
```
{
"status": "true",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ2YWx1ZSI6ImdtYWlsLmNvbSIsImV4cCI6MTY5ODc1ODIyNn0.eVrNACUY93g-5tu8fxb2BEOs1wn2iCe8wVpUYU6OLSE",
"username": "shivamsourav",
"message": "OTP authenticated successfully"
}
```

_Now, let's see the magic! 🪄💫_

Now both these API calls were captured as a testcase and should be visible on the Keploy CLI. You should be seeing an app named `keploy folder` with the test cases we just captured and data mocks created.

### Run the captured testcases

Now that we have our testcase captured, run the test file.

```shell
keploy test -c "sudo docker run -p 3001:3001 --rm --network <networkName> --name ginRedisApp gin-app:1.0" --delay 10
```

So no need to setup dependencies like Redis, web-go locally or write mocks for your testing.

**The application thinks it's talking to Redis 😄**

We will get output something like this:

![TestRun](./img/testRunFail.png)

#### Let's add token to Noisy field:

In `test-2.yml` go to the noisefield and `-body.token` in noise. Now, it's the time to run the test cases again.

```bash
keploy test -c "sudo docker run -p 3001:3001 --rm --network <networkName> --name ginRedisApp gin-app:1.0" --delay 10
```

This time all the test cases will pass.
![testruns](./img/testRunPass.png?raw=true "Recent testruns")

## Run app Natively on local machine

Keploy can be installed on Linux directly and on Windows with the help of WSL. Based on your system archieture, install the keploy latest binary release

**1. AMD Architecture**

```shell
curl --silent --location "https://github.com/keploy/keploy/releases/latest/download/keploy_linux_amd64.tar.gz" | tar xz -C /tmp

sudo mkdir -p /usr/local/bin && sudo mv /tmp/keploy /usr/local/bin && keploy
```

<details>
<summary> 2. ARM Architecture </summary>

```shell
curl --silent --location "https://github.com/keploy/keploy/releases/latest/download/keploy_linux_arm64.tar.gz" | tar xz -C /tmp

sudo mkdir -p /usr/local/bin && sudo mv /tmp/keploy /usr/local/bin && keploy
```

</details>

#### Let's start the Redis Instance

Spin up your Redis container using

```shell
sudo docker run -p 6379:6379 -d --name myredis redis
```

### Capture the testcases

Now, we will create the binary of our application:-

```zsh
go build -o gin-redis
```

Once we have our binary file ready,this command will start the recording of API calls using ebpf:-

```shell
sudo -E keploy record -c "./gin-redis"
```

Make API Calls using Hoppscotch, Postman or cURL command. Keploy with capture those calls to generate the test-suites containing testcases and data mocks.

### Generate testcases

To generate testcases we just need to **make some API calls.** You can use [Postman](https://www.postman.com/), [Hoppscotch](https://hoppscotch.io/), or simply `curl`

**1. Request OTP**

```bash
curl --location 'localhost:3001/api/[email protected]&username=shivamsourav'
```

this will return the OTP response.

```
{
"status": "true",
"message": "OTP Generated successfully",
"otp": "5486"
}
```

**2. Verify OTP**

```bash
curl --location 'localhost:3001/api/verifyCode' \
--header 'Content-Type: application/json' \
--data-raw '{
"otp":2121,
"email":"[email protected]"
}'

```

this will return the OTP verification response.
```
{
"status": "true",
"token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ2YWx1ZSI6ImdtYWlsLmNvbSIsImV4cCI6MTY5ODc1ODIyNn0.eVrNACUY93g-5tu8fxb2BEOs1wn2iCe8wVpUYU6OLSE",
"username": "shivamsourav",
"message": "OTP authenticated successfully"
}
```

You'll be able to see new test file and mock file generated in your project codebase locally.

### Run the Test Mode

Run this command on your terminal to run the testcases and generate the test coverage report:-

```shell
sudo -E keploy test -c "./gin-redis" --delay 10
```

> Note: If delay value is not defined, by default it would be `5`.
So no need to setup dependencies like Redis, web-go locally or write mocks for your testing.

**The application thinks it's talking to Redis 😄**

We will get output something like this:

![TestRun](./img/testRunFail.png)

#### Let's add token to Noisy field:

In `test-2.yml` go to the noisefield and `-body.token` in noise. Now, it's the time to run the test cases again.

```bash
sudo -E keploy test -c "./gin-redis" --delay 10
```

This time all the test cases will pass.

![testruns](./img/testRunPass.png?raw=true "Recent testruns")
74 changes: 74 additions & 0 deletions gin-redis/config/config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
package config

import (
"os"
"strconv"
)

type Config struct {
AppName string
DATABASE string
AppEnv string
SqlPrefix string
DBUserName string
PORT string
DBPassword string
DBHostWriter string
ServerPort string
DBHostReader string
DBPort string
DBName string
AMPQ_URL string
DAILYPASSSERVICE string
DBMaxOpenConnections int
EmailPassword string
DBMaxIdleConnections int
JWT string
MongoPort string
MongoUsername string
MongoPassword string
CloudName string
CloudSecret string
CloudPublic string
SuperAdmin string
}

var config Config

// Should run at the very beginning, before any other package
// or code.
func init() {
appEnv := os.Getenv("APP_ENV")
if len(appEnv) == 0 {
appEnv = "dev"
}
config.AppName = os.Getenv("SERVICE_NAME")
config.AppEnv = appEnv
config.SqlPrefix = "/* " + config.AppName + " - " + config.AppEnv + "*/"
config.DBUserName = os.Getenv("DB_USERNAME")
config.JWT = os.Getenv("JWT_TOKEN")
config.DBHostWriter = os.Getenv("DB_HOST_WRITER")
config.DBPort = os.Getenv("DB_PORT")
config.DBPassword = os.Getenv("DB_PASSWORD")
config.DBName = os.Getenv("DB_NAME")
config.DATABASE = os.Getenv("DATABASE")
config.AMPQ_URL = os.Getenv("AMPQ_URL")
config.PORT = os.Getenv("PORT")
config.DAILYPASSSERVICE = os.Getenv("DAILYPASSSERVICE")
config.EmailPassword = os.Getenv("EMAIL_PASSWORD")
config.DBMaxIdleConnections, _ = strconv.Atoi(os.Getenv("DB_MAX_IDLE_CONENCTION"))
config.DBMaxOpenConnections, _ = strconv.Atoi(os.Getenv("DB_MAX_OPEN_CONNECTIONS"))
config.DBHostReader = os.Getenv("DB_HOST_READER")
config.MongoPort = os.Getenv("MONGO_PORT")
config.MongoUsername = os.Getenv("MongoUsername")
config.MongoPassword = os.Getenv("MongoPassword")
config.CloudSecret = os.Getenv("CloudSecret")
config.CloudName = os.Getenv("CloudName")
config.CloudPublic = os.Getenv("CloudPublic")
config.SuperAdmin = os.Getenv("SuperAdmin")
config.ServerPort = os.Getenv("PORT")
}

func Get() Config {
return config
}
34 changes: 34 additions & 0 deletions gin-redis/constants/contants.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package constants

const VerificationMailTemplate = `<html>
<head>
<title>Href Attribute Example</title>
</head>
<body>
<h1>Href Attribute Example</h1>
<p>
<a href="https://www.freecodecamp.org/contribute/">The freeCodeCamp Contribution Page</a> shows you how and where you can contribute to freeCodeCamp's community and growth.
</p>
<p>
Your verification code is: %d
</p>
</body>
</html>`

const VerifyYourself = "Verify yourself with Influenza"

const API_SUCCESS_STATUS = "Success"

const API_FAILED_STATUS = "Failed"

const ApiFailStatus = "Fail"

var INVALID_TOKEN_RESPONSE = map[string]interface{}{
"status": ApiFailStatus,
"message": "Invalid or No Token",
}

var INVALID_SUPER_ADMIN = map[string]interface{}{
"status": ApiFailStatus,
"message": "Go back son",
}
Loading

0 comments on commit 5dcdf2b

Please sign in to comment.