Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Token Verification Enhancements #205

Closed
wants to merge 5 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions client/token.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,3 +70,15 @@ func (c *Client) ValidateTokenchain(user_did string, smartContractChainValidatio
}
return &br, nil
}

func (c *Client) ValidateToken(token string) (*model.BasicResponse, error) {
q := make(map[string]string)
q["token"] = token

var br model.BasicResponse
err := c.sendJSONRequest("GET", setup.APIValidateToken, q, nil, &br)
if err != nil {
return nil, err
}
return &br, nil
}
9 changes: 9 additions & 0 deletions command/command.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ const (
PinTokenCmd string = "pinToken"
RecoverTokensCmd string = "recoverToken"
ValidateTokenchainCmd string = "validatetokenchain"
ValidateTokenCmd string = "validatetoken"
)

var commands = []string{VersionCmd,
Expand Down Expand Up @@ -144,6 +145,7 @@ var commands = []string{VersionCmd,
RecoverTokensCmd,
CheckQuorumStatusCmd,
ValidateTokenchainCmd,
ValidateTokenCmd,
}

var commandsHelp = []string{"To get tool version",
Expand Down Expand Up @@ -193,6 +195,11 @@ var commandsHelp = []string{"To get tool version",
"This command will initiate a self RBT transfer",
"This command will unpledge all the pledged tokens",
"This command will unpledge all PoW based pledge tokens and drop the unpledgequeue table",
"This command will pin the token",
"This command will recover the token",
"This command will check the quorum status",
"This command will validate the token chain",
"This command will validate the token",
}

type Command struct {
Expand Down Expand Up @@ -650,6 +657,8 @@ func Run(args []string) {
cmd.RecoverTokens()
case ValidateTokenchainCmd:
cmd.ValidateTokenchain()
case ValidateTokenCmd:
cmd.ValidateToken()
default:
cmd.log.Error("Invalid command")
}
Expand Down
24 changes: 24 additions & 0 deletions command/token.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,3 +70,27 @@ func (cmd *Command) ValidateTokenchain() {

cmd.log.Info("Tokenchain validated successfully", "msg", br.Message)
}

func (cmd *Command) ValidateToken() {
if cmd.token == "" {
cmd.log.Info("Token cannot be empty")
fmt.Print("Enter Token : ")
_, err := fmt.Scan(&cmd.token)
if err != nil {
cmd.log.Error("Failed to get tokenhash")
return
}
}
br, err := cmd.c.ValidateToken(cmd.token)
if err != nil {
cmd.log.Error("failed to validate token", "err", err)
return
}

if !br.Status {
cmd.log.Error("failed to validate token %s", cmd.token, "msg", br.Message)
return
}
cmd.log.Info("Token %s validated successfully ", cmd.token, "msg", br.Message)

}
1 change: 1 addition & 0 deletions core/core.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ const (
TestNetDir string = "TestNet"
TestNetDIDDir string = "TestNetDID/"
MaxDecimalPlaces int = 3
TokenValidatorURL string = "http://103.209.145.177:8000"
)

const (
Expand Down
97 changes: 97 additions & 0 deletions core/token.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ package core

import (
"bytes"
"encoding/json"
"fmt"
"io"
"net/http"
"strings"
"time"
Expand Down Expand Up @@ -34,6 +36,16 @@ type TCBSyncReply struct {
TCBlock [][]byte `json:"tc_block"`
}

// TokenVerificationRequest struct
type TokenVerificationRequest struct {
Tokens []string `json:"tokens"`
}

// TokenVerificationResponse struct
type TokenVerificationResponse struct {
Results map[string]bool `json:"results"`
}

func (c *Core) SetupToken() {
c.l.AddRoute(APISyncTokenChain, "POST", c.syncTokenChain)
}
Expand Down Expand Up @@ -528,3 +540,88 @@ func (c *Core) GetpinnedTokens(did string) ([]wallet.Token, error) {
}
return requiredTokens, nil
}

func (c *Core) ValidateToken(token string) (*model.BasicResponse, error) {

response := &model.BasicResponse{
Status: false,
Message: "Invalid token hash",
}

// commented out for now, #TODO
/* if c.testNet {
response.Message = "validate token is not available in test net"
response.Result = "invalid operation"
return response, fmt.Errorf("validate token is not available in test net")
} */
// Get token hash from IPFS
tokenHashReader, err := c.ipfs.Cat(token)
if err != nil {
return response, fmt.Errorf("error getting token hash from IPFS: %v", err)
}
defer tokenHashReader.Close()

// Read token hash from io.ReadCloser
var tokenHashBuf bytes.Buffer
if _, err := io.Copy(&tokenHashBuf, tokenHashReader); err != nil {
return response, fmt.Errorf("error reading token hash: %v", err)
}
tokenHash := tokenHashBuf.String()
// Trim any leading/trailing whitespace, including newlines
tokenHash = strings.TrimSpace(tokenHash)
/*
// Length check (should be 67 characters as per your requirements)
if len(tokenHash) != 67 {
return response, fmt.Errorf("invalid token length: %s, length is %v", tokenHash, len(tokenHash))
} */

// Call the VerifyTokens function from the tokenverifier package
verifyResponse, err := VerifyTokens(TokenValidatorURL, []string{tokenHash})
if err != nil {
return response, fmt.Errorf("token verification API call failed: %v", err)
}

// Check the result from the API response
isValid, tokenFound := verifyResponse.Results[tokenHash]
if !tokenFound {
return response, fmt.Errorf("token not found in verification response")
}

if isValid {
response.Status = true
response.Message = fmt.Sprintf("Token %s is valid", token)
} else {
response.Message = fmt.Sprintf("Token %s is invalid", token)
}

return response, nil
}

// VerifyTokens function sends the API request and handles the response
func VerifyTokens(serverURL string, tokens []string) (TokenVerificationResponse, error) {
url := fmt.Sprintf("%s/verify", serverURL)

requestBody := TokenVerificationRequest{Tokens: tokens}
jsonData, err := json.Marshal(requestBody)
if err != nil {
return TokenVerificationResponse{}, fmt.Errorf("error marshalling request: %v", err)
}

resp, err := http.Post(url, "application/json", bytes.NewBuffer(jsonData))
if err != nil {
return TokenVerificationResponse{}, fmt.Errorf("error sending request: %v", err)
}
defer resp.Body.Close()

if resp.StatusCode != http.StatusOK {
return TokenVerificationResponse{}, fmt.Errorf("API request failed with status: %d", resp.StatusCode)
}

var responseBody TokenVerificationResponse
err = json.NewDecoder(resp.Body).Decode(&responseBody)
if err != nil {
return TokenVerificationResponse{}, fmt.Errorf("error decoding response: %v", err)
}

return responseBody, nil
}
1 change: 1 addition & 0 deletions server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,7 @@ func (s *Server) RegisterRoutes() {
s.AddRoute(setup.APIInitiatePinRBT, "POST", s.AuthHandle(s.APIInitiatePinRBT, true, s.AuthError, false))
s.AddRoute(setup.APIRecoverRBT, "POST", s.AuthHandle(s.APIRecoverRBT, true, s.AuthError, false))
s.AddRoute(setup.APIValidateTokenChain, "GET", s.AuthHandle(s.APIValidateTokenChain, false, s.AuthError, false))
s.AddRoute(setup.APIValidateToken, "GET", s.AuthHandle(s.APIValidateToken, false, s.AuthError, false))
}

func (s *Server) ExitFunc() error {
Expand Down
10 changes: 10 additions & 0 deletions server/tokens.go
Original file line number Diff line number Diff line change
Expand Up @@ -340,3 +340,13 @@ func (s *Server) APIValidateTokenChain(req *ensweb.Request) *ensweb.Result {

return s.RenderJSON(req, br, http.StatusOK)
}

func (s *Server) APIValidateToken(req *ensweb.Request) *ensweb.Result {
token := s.GetQuerry(req, "token")
br, err := s.c.ValidateToken(token)
if err != nil {
s.log.Error("Failed to validate token ", err)
return s.BasicResponse(req, false, "Failed to validate token : "+err.Error(), nil)
}
return s.RenderJSON(req, br, http.StatusOK)
}
1 change: 1 addition & 0 deletions setup/setup.go
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ const (
APIInitiatePinRBT string = "/api/initiate-pin-token"
APIRecoverRBT string = "/api/recover-token"
APIValidateTokenChain string = "/api/validate-token-chain"
APIValidateToken string = "/api/validate-token"
)

// jwt.RegisteredClaims
Expand Down