merger + auth fix
This commit is contained in:
commit
22ec5d3ff8
|
|
@ -55,6 +55,7 @@ CREATE TABLE IF NOT EXISTS bets (
|
||||||
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
|
||||||
is_shop_bet BOOLEAN NOT NULL,
|
is_shop_bet BOOLEAN NOT NULL,
|
||||||
|
outcomes_hash TEXT NOT NULL,
|
||||||
UNIQUE(cashout_id),
|
UNIQUE(cashout_id),
|
||||||
CHECK (
|
CHECK (
|
||||||
user_id IS NOT NULL
|
user_id IS NOT NULL
|
||||||
|
|
@ -310,7 +311,7 @@ ALTER TABLE bets
|
||||||
ADD CONSTRAINT fk_bets_users FOREIGN KEY (user_id) REFERENCES users(id),
|
ADD CONSTRAINT fk_bets_users FOREIGN KEY (user_id) REFERENCES users(id),
|
||||||
ADD CONSTRAINT fk_bets_branches FOREIGN KEY (branch_id) REFERENCES branches(id);
|
ADD CONSTRAINT fk_bets_branches FOREIGN KEY (branch_id) REFERENCES branches(id);
|
||||||
ALTER TABLE wallets
|
ALTER TABLE wallets
|
||||||
ADD CONSTRAINT fk_wallets_users FOREIGN KEY (user_id) REFERENCES users(id);
|
ADD CONSTRAINT fk_wallets_users FOREIGN KEY (user_id) REFERENCES users(id),
|
||||||
ADD COLUMN currency VARCHAR(3) NOT NULL DEFAULT 'ETB';
|
ADD COLUMN currency VARCHAR(3) NOT NULL DEFAULT 'ETB';
|
||||||
ALTER TABLE customer_wallets
|
ALTER TABLE customer_wallets
|
||||||
ADD CONSTRAINT fk_customer_wallets_customers FOREIGN KEY (customer_id) REFERENCES users(id),
|
ADD CONSTRAINT fk_customer_wallets_customers FOREIGN KEY (customer_id) REFERENCES users(id),
|
||||||
|
|
|
||||||
|
|
@ -1,18 +1,18 @@
|
||||||
-- CREATE TABLE virtual_games (
|
CREATE TABLE IF NOT EXISTS virtual_games (
|
||||||
-- id BIGSERIAL PRIMARY KEY,
|
id BIGSERIAL PRIMARY KEY,
|
||||||
-- name VARCHAR(255) NOT NULL,
|
name VARCHAR(255) NOT NULL,
|
||||||
-- provider VARCHAR(100) NOT NULL,
|
provider VARCHAR(100) NOT NULL,
|
||||||
-- category VARCHAR(100) NOT NULL,
|
category VARCHAR(100) NOT NULL,
|
||||||
-- min_bet DECIMAL(15,2) NOT NULL,
|
min_bet DECIMAL(15,2) NOT NULL,
|
||||||
-- max_bet DECIMAL(15,2) NOT NULL,
|
max_bet DECIMAL(15,2) NOT NULL,
|
||||||
-- volatility VARCHAR(50) NOT NULL,
|
volatility VARCHAR(50) NOT NULL,
|
||||||
-- rtp DECIMAL(5,2) NOT NULL,
|
rtp DECIMAL(5,2) NOT NULL,
|
||||||
-- is_featured BOOLEAN DEFAULT false,
|
is_featured BOOLEAN DEFAULT false,
|
||||||
-- popularity_score INTEGER DEFAULT 0,
|
popularity_score INTEGER DEFAULT 0,
|
||||||
-- thumbnail_url TEXT,
|
thumbnail_url TEXT,
|
||||||
-- created_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
|
created_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP,
|
||||||
-- updated_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP
|
updated_at TIMESTAMPTZ DEFAULT CURRENT_TIMESTAMP
|
||||||
-- );
|
);
|
||||||
|
|
||||||
CREATE TABLE user_game_interactions (
|
CREATE TABLE user_game_interactions (
|
||||||
id BIGSERIAL PRIMARY KEY,
|
id BIGSERIAL PRIMARY KEY,
|
||||||
|
|
|
||||||
|
|
@ -9,9 +9,10 @@ INSERT INTO bets (
|
||||||
user_id,
|
user_id,
|
||||||
is_shop_bet,
|
is_shop_bet,
|
||||||
cashout_id,
|
cashout_id,
|
||||||
company_id
|
company_id,
|
||||||
|
outcomes_hash
|
||||||
)
|
)
|
||||||
VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)
|
VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11)
|
||||||
RETURNING *;
|
RETURNING *;
|
||||||
-- name: CreateBetOutcome :copyfrom
|
-- name: CreateBetOutcome :copyfrom
|
||||||
INSERT INTO bet_outcomes (
|
INSERT INTO bet_outcomes (
|
||||||
|
|
@ -83,6 +84,11 @@ WHERE event_id = $1;
|
||||||
SELECT *
|
SELECT *
|
||||||
FROM bet_outcomes
|
FROM bet_outcomes
|
||||||
WHERE bet_id = $1;
|
WHERE bet_id = $1;
|
||||||
|
-- name: GetBetCount :one
|
||||||
|
SELECT COUNT(*)
|
||||||
|
FROM bets
|
||||||
|
where user_id = $1
|
||||||
|
AND outcomes_hash = $2;
|
||||||
-- name: UpdateCashOut :exec
|
-- name: UpdateCashOut :exec
|
||||||
UPDATE bets
|
UPDATE bets
|
||||||
SET cashed_out = $2,
|
SET cashed_out = $2,
|
||||||
|
|
|
||||||
|
|
@ -61,7 +61,8 @@ SET name = COALESCE(sqlc.narg(name), name),
|
||||||
location = COALESCE(sqlc.narg(location), location),
|
location = COALESCE(sqlc.narg(location), location),
|
||||||
branch_manager_id = COALESCE(sqlc.narg(branch_manager_id), branch_manager_id),
|
branch_manager_id = COALESCE(sqlc.narg(branch_manager_id), branch_manager_id),
|
||||||
company_id = COALESCE(sqlc.narg(company_id), company_id),
|
company_id = COALESCE(sqlc.narg(company_id), company_id),
|
||||||
is_self_owned = COALESCE(sqlc.narg(is_self_owned), is_self_owned)
|
is_self_owned = COALESCE(sqlc.narg(is_self_owned), is_self_owned),
|
||||||
|
is_active = COALESCE(sqlc.narg(is_active), is_active)
|
||||||
WHERE id = $1
|
WHERE id = $1
|
||||||
RETURNING *;
|
RETURNING *;
|
||||||
-- name: DeleteBranch :exec
|
-- name: DeleteBranch :exec
|
||||||
|
|
|
||||||
|
|
@ -22,23 +22,25 @@ INSERT INTO bets (
|
||||||
user_id,
|
user_id,
|
||||||
is_shop_bet,
|
is_shop_bet,
|
||||||
cashout_id,
|
cashout_id,
|
||||||
company_id
|
company_id,
|
||||||
|
outcomes_hash
|
||||||
)
|
)
|
||||||
VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10)
|
VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10, $11)
|
||||||
RETURNING id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet
|
RETURNING id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash
|
||||||
`
|
`
|
||||||
|
|
||||||
type CreateBetParams struct {
|
type CreateBetParams struct {
|
||||||
Amount int64 `json:"amount"`
|
Amount int64 `json:"amount"`
|
||||||
TotalOdds float32 `json:"total_odds"`
|
TotalOdds float32 `json:"total_odds"`
|
||||||
Status int32 `json:"status"`
|
Status int32 `json:"status"`
|
||||||
FullName string `json:"full_name"`
|
FullName string `json:"full_name"`
|
||||||
PhoneNumber string `json:"phone_number"`
|
PhoneNumber string `json:"phone_number"`
|
||||||
BranchID pgtype.Int8 `json:"branch_id"`
|
BranchID pgtype.Int8 `json:"branch_id"`
|
||||||
UserID pgtype.Int8 `json:"user_id"`
|
UserID pgtype.Int8 `json:"user_id"`
|
||||||
IsShopBet bool `json:"is_shop_bet"`
|
IsShopBet bool `json:"is_shop_bet"`
|
||||||
CashoutID string `json:"cashout_id"`
|
CashoutID string `json:"cashout_id"`
|
||||||
CompanyID pgtype.Int8 `json:"company_id"`
|
CompanyID pgtype.Int8 `json:"company_id"`
|
||||||
|
OutcomesHash string `json:"outcomes_hash"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (q *Queries) CreateBet(ctx context.Context, arg CreateBetParams) (Bet, error) {
|
func (q *Queries) CreateBet(ctx context.Context, arg CreateBetParams) (Bet, error) {
|
||||||
|
|
@ -53,6 +55,7 @@ func (q *Queries) CreateBet(ctx context.Context, arg CreateBetParams) (Bet, erro
|
||||||
arg.IsShopBet,
|
arg.IsShopBet,
|
||||||
arg.CashoutID,
|
arg.CashoutID,
|
||||||
arg.CompanyID,
|
arg.CompanyID,
|
||||||
|
arg.OutcomesHash,
|
||||||
)
|
)
|
||||||
var i Bet
|
var i Bet
|
||||||
err := row.Scan(
|
err := row.Scan(
|
||||||
|
|
@ -70,6 +73,7 @@ func (q *Queries) CreateBet(ctx context.Context, arg CreateBetParams) (Bet, erro
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
)
|
)
|
||||||
return i, err
|
return i, err
|
||||||
}
|
}
|
||||||
|
|
@ -111,7 +115,7 @@ func (q *Queries) DeleteBetOutcome(ctx context.Context, betID int64) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetAllBets = `-- name: GetAllBets :many
|
const GetAllBets = `-- name: GetAllBets :many
|
||||||
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes
|
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash, outcomes
|
||||||
FROM bet_with_outcomes
|
FROM bet_with_outcomes
|
||||||
wHERE (
|
wHERE (
|
||||||
branch_id = $1
|
branch_id = $1
|
||||||
|
|
@ -157,6 +161,7 @@ func (q *Queries) GetAllBets(ctx context.Context, arg GetAllBetsParams) ([]BetWi
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
&i.Outcomes,
|
&i.Outcomes,
|
||||||
); err != nil {
|
); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -170,7 +175,7 @@ func (q *Queries) GetAllBets(ctx context.Context, arg GetAllBetsParams) ([]BetWi
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetBetByBranchID = `-- name: GetBetByBranchID :many
|
const GetBetByBranchID = `-- name: GetBetByBranchID :many
|
||||||
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes
|
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash, outcomes
|
||||||
FROM bet_with_outcomes
|
FROM bet_with_outcomes
|
||||||
WHERE branch_id = $1
|
WHERE branch_id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -199,6 +204,7 @@ func (q *Queries) GetBetByBranchID(ctx context.Context, branchID pgtype.Int8) ([
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
&i.Outcomes,
|
&i.Outcomes,
|
||||||
); err != nil {
|
); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -212,7 +218,7 @@ func (q *Queries) GetBetByBranchID(ctx context.Context, branchID pgtype.Int8) ([
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetBetByCashoutID = `-- name: GetBetByCashoutID :one
|
const GetBetByCashoutID = `-- name: GetBetByCashoutID :one
|
||||||
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes
|
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash, outcomes
|
||||||
FROM bet_with_outcomes
|
FROM bet_with_outcomes
|
||||||
WHERE cashout_id = $1
|
WHERE cashout_id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -235,13 +241,14 @@ func (q *Queries) GetBetByCashoutID(ctx context.Context, cashoutID string) (BetW
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
&i.Outcomes,
|
&i.Outcomes,
|
||||||
)
|
)
|
||||||
return i, err
|
return i, err
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetBetByID = `-- name: GetBetByID :one
|
const GetBetByID = `-- name: GetBetByID :one
|
||||||
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes
|
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash, outcomes
|
||||||
FROM bet_with_outcomes
|
FROM bet_with_outcomes
|
||||||
WHERE id = $1
|
WHERE id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -264,13 +271,14 @@ func (q *Queries) GetBetByID(ctx context.Context, id int64) (BetWithOutcome, err
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
&i.Outcomes,
|
&i.Outcomes,
|
||||||
)
|
)
|
||||||
return i, err
|
return i, err
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetBetByUserID = `-- name: GetBetByUserID :many
|
const GetBetByUserID = `-- name: GetBetByUserID :many
|
||||||
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes
|
SELECT id, amount, total_odds, status, full_name, phone_number, company_id, branch_id, user_id, cashed_out, cashout_id, created_at, updated_at, is_shop_bet, outcomes_hash, outcomes
|
||||||
FROM bet_with_outcomes
|
FROM bet_with_outcomes
|
||||||
WHERE user_id = $1
|
WHERE user_id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -299,6 +307,7 @@ func (q *Queries) GetBetByUserID(ctx context.Context, userID pgtype.Int8) ([]Bet
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
&i.IsShopBet,
|
&i.IsShopBet,
|
||||||
|
&i.OutcomesHash,
|
||||||
&i.Outcomes,
|
&i.Outcomes,
|
||||||
); err != nil {
|
); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -311,6 +320,25 @@ func (q *Queries) GetBetByUserID(ctx context.Context, userID pgtype.Int8) ([]Bet
|
||||||
return items, nil
|
return items, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const GetBetCount = `-- name: GetBetCount :one
|
||||||
|
SELECT COUNT(*)
|
||||||
|
FROM bets
|
||||||
|
where user_id = $1
|
||||||
|
AND outcomes_hash = $2
|
||||||
|
`
|
||||||
|
|
||||||
|
type GetBetCountParams struct {
|
||||||
|
UserID pgtype.Int8 `json:"user_id"`
|
||||||
|
OutcomesHash string `json:"outcomes_hash"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func (q *Queries) GetBetCount(ctx context.Context, arg GetBetCountParams) (int64, error) {
|
||||||
|
row := q.db.QueryRow(ctx, GetBetCount, arg.UserID, arg.OutcomesHash)
|
||||||
|
var count int64
|
||||||
|
err := row.Scan(&count)
|
||||||
|
return count, err
|
||||||
|
}
|
||||||
|
|
||||||
const GetBetOutcomeByBetID = `-- name: GetBetOutcomeByBetID :many
|
const GetBetOutcomeByBetID = `-- name: GetBetOutcomeByBetID :many
|
||||||
SELECT id, bet_id, sport_id, event_id, odd_id, home_team_name, away_team_name, market_id, market_name, odd, odd_name, odd_header, odd_handicap, status, expires
|
SELECT id, bet_id, sport_id, event_id, odd_id, home_team_name, away_team_name, market_id, market_name, odd, odd_name, odd_header, odd_handicap, status, expires
|
||||||
FROM bet_outcomes
|
FROM bet_outcomes
|
||||||
|
|
|
||||||
|
|
@ -443,7 +443,8 @@ SET name = COALESCE($2, name),
|
||||||
location = COALESCE($3, location),
|
location = COALESCE($3, location),
|
||||||
branch_manager_id = COALESCE($4, branch_manager_id),
|
branch_manager_id = COALESCE($4, branch_manager_id),
|
||||||
company_id = COALESCE($5, company_id),
|
company_id = COALESCE($5, company_id),
|
||||||
is_self_owned = COALESCE($6, is_self_owned)
|
is_self_owned = COALESCE($6, is_self_owned),
|
||||||
|
is_active = COALESCE($7, is_active)
|
||||||
WHERE id = $1
|
WHERE id = $1
|
||||||
RETURNING id, name, location, is_active, wallet_id, branch_manager_id, company_id, is_self_owned, created_at, updated_at
|
RETURNING id, name, location, is_active, wallet_id, branch_manager_id, company_id, is_self_owned, created_at, updated_at
|
||||||
`
|
`
|
||||||
|
|
@ -455,6 +456,7 @@ type UpdateBranchParams struct {
|
||||||
BranchManagerID pgtype.Int8 `json:"branch_manager_id"`
|
BranchManagerID pgtype.Int8 `json:"branch_manager_id"`
|
||||||
CompanyID pgtype.Int8 `json:"company_id"`
|
CompanyID pgtype.Int8 `json:"company_id"`
|
||||||
IsSelfOwned pgtype.Bool `json:"is_self_owned"`
|
IsSelfOwned pgtype.Bool `json:"is_self_owned"`
|
||||||
|
IsActive pgtype.Bool `json:"is_active"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (q *Queries) UpdateBranch(ctx context.Context, arg UpdateBranchParams) (Branch, error) {
|
func (q *Queries) UpdateBranch(ctx context.Context, arg UpdateBranchParams) (Branch, error) {
|
||||||
|
|
@ -465,6 +467,7 @@ func (q *Queries) UpdateBranch(ctx context.Context, arg UpdateBranchParams) (Bra
|
||||||
arg.BranchManagerID,
|
arg.BranchManagerID,
|
||||||
arg.CompanyID,
|
arg.CompanyID,
|
||||||
arg.IsSelfOwned,
|
arg.IsSelfOwned,
|
||||||
|
arg.IsActive,
|
||||||
)
|
)
|
||||||
var i Branch
|
var i Branch
|
||||||
err := row.Scan(
|
err := row.Scan(
|
||||||
|
|
|
||||||
|
|
@ -56,20 +56,21 @@ func (ns NullReferralstatus) Value() (driver.Value, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
type Bet struct {
|
type Bet struct {
|
||||||
ID int64 `json:"id"`
|
ID int64 `json:"id"`
|
||||||
Amount int64 `json:"amount"`
|
Amount int64 `json:"amount"`
|
||||||
TotalOdds float32 `json:"total_odds"`
|
TotalOdds float32 `json:"total_odds"`
|
||||||
Status int32 `json:"status"`
|
Status int32 `json:"status"`
|
||||||
FullName string `json:"full_name"`
|
FullName string `json:"full_name"`
|
||||||
PhoneNumber string `json:"phone_number"`
|
PhoneNumber string `json:"phone_number"`
|
||||||
CompanyID pgtype.Int8 `json:"company_id"`
|
CompanyID pgtype.Int8 `json:"company_id"`
|
||||||
BranchID pgtype.Int8 `json:"branch_id"`
|
BranchID pgtype.Int8 `json:"branch_id"`
|
||||||
UserID pgtype.Int8 `json:"user_id"`
|
UserID pgtype.Int8 `json:"user_id"`
|
||||||
CashedOut bool `json:"cashed_out"`
|
CashedOut bool `json:"cashed_out"`
|
||||||
CashoutID string `json:"cashout_id"`
|
CashoutID string `json:"cashout_id"`
|
||||||
CreatedAt pgtype.Timestamp `json:"created_at"`
|
CreatedAt pgtype.Timestamp `json:"created_at"`
|
||||||
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
||||||
IsShopBet bool `json:"is_shop_bet"`
|
IsShopBet bool `json:"is_shop_bet"`
|
||||||
|
OutcomesHash string `json:"outcomes_hash"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type BetOutcome struct {
|
type BetOutcome struct {
|
||||||
|
|
@ -91,21 +92,22 @@ type BetOutcome struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
type BetWithOutcome struct {
|
type BetWithOutcome struct {
|
||||||
ID int64 `json:"id"`
|
ID int64 `json:"id"`
|
||||||
Amount int64 `json:"amount"`
|
Amount int64 `json:"amount"`
|
||||||
TotalOdds float32 `json:"total_odds"`
|
TotalOdds float32 `json:"total_odds"`
|
||||||
Status int32 `json:"status"`
|
Status int32 `json:"status"`
|
||||||
FullName string `json:"full_name"`
|
FullName string `json:"full_name"`
|
||||||
PhoneNumber string `json:"phone_number"`
|
PhoneNumber string `json:"phone_number"`
|
||||||
CompanyID pgtype.Int8 `json:"company_id"`
|
CompanyID pgtype.Int8 `json:"company_id"`
|
||||||
BranchID pgtype.Int8 `json:"branch_id"`
|
BranchID pgtype.Int8 `json:"branch_id"`
|
||||||
UserID pgtype.Int8 `json:"user_id"`
|
UserID pgtype.Int8 `json:"user_id"`
|
||||||
CashedOut bool `json:"cashed_out"`
|
CashedOut bool `json:"cashed_out"`
|
||||||
CashoutID string `json:"cashout_id"`
|
CashoutID string `json:"cashout_id"`
|
||||||
CreatedAt pgtype.Timestamp `json:"created_at"`
|
CreatedAt pgtype.Timestamp `json:"created_at"`
|
||||||
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
||||||
IsShopBet bool `json:"is_shop_bet"`
|
IsShopBet bool `json:"is_shop_bet"`
|
||||||
Outcomes []BetOutcome `json:"outcomes"`
|
OutcomesHash string `json:"outcomes_hash"`
|
||||||
|
Outcomes []BetOutcome `json:"outcomes"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Branch struct {
|
type Branch struct {
|
||||||
|
|
@ -204,6 +206,15 @@ type Event struct {
|
||||||
Source pgtype.Text `json:"source"`
|
Source pgtype.Text `json:"source"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ExchangeRate struct {
|
||||||
|
ID int32 `json:"id"`
|
||||||
|
FromCurrency string `json:"from_currency"`
|
||||||
|
ToCurrency string `json:"to_currency"`
|
||||||
|
Rate pgtype.Numeric `json:"rate"`
|
||||||
|
ValidUntil pgtype.Timestamp `json:"valid_until"`
|
||||||
|
CreatedAt pgtype.Timestamp `json:"created_at"`
|
||||||
|
}
|
||||||
|
|
||||||
type League struct {
|
type League struct {
|
||||||
ID int64 `json:"id"`
|
ID int64 `json:"id"`
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
|
|
@ -470,6 +481,7 @@ type Wallet struct {
|
||||||
IsActive bool `json:"is_active"`
|
IsActive bool `json:"is_active"`
|
||||||
CreatedAt pgtype.Timestamp `json:"created_at"`
|
CreatedAt pgtype.Timestamp `json:"created_at"`
|
||||||
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
UpdatedAt pgtype.Timestamp `json:"updated_at"`
|
||||||
|
Currency string `json:"currency"`
|
||||||
BonusBalance pgtype.Numeric `json:"bonus_balance"`
|
BonusBalance pgtype.Numeric `json:"bonus_balance"`
|
||||||
CashBalance pgtype.Numeric `json:"cash_balance"`
|
CashBalance pgtype.Numeric `json:"cash_balance"`
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -49,7 +49,7 @@ INSERT INTO wallets (
|
||||||
user_id
|
user_id
|
||||||
)
|
)
|
||||||
VALUES ($1, $2, $3, $4)
|
VALUES ($1, $2, $3, $4)
|
||||||
RETURNING id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, bonus_balance, cash_balance
|
RETURNING id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, currency, bonus_balance, cash_balance
|
||||||
`
|
`
|
||||||
|
|
||||||
type CreateWalletParams struct {
|
type CreateWalletParams struct {
|
||||||
|
|
@ -77,6 +77,7 @@ func (q *Queries) CreateWallet(ctx context.Context, arg CreateWalletParams) (Wal
|
||||||
&i.IsActive,
|
&i.IsActive,
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
|
&i.Currency,
|
||||||
&i.BonusBalance,
|
&i.BonusBalance,
|
||||||
&i.CashBalance,
|
&i.CashBalance,
|
||||||
)
|
)
|
||||||
|
|
@ -143,7 +144,7 @@ func (q *Queries) GetAllBranchWallets(ctx context.Context) ([]GetAllBranchWallet
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetAllWallets = `-- name: GetAllWallets :many
|
const GetAllWallets = `-- name: GetAllWallets :many
|
||||||
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, bonus_balance, cash_balance
|
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, currency, bonus_balance, cash_balance
|
||||||
FROM wallets
|
FROM wallets
|
||||||
`
|
`
|
||||||
|
|
||||||
|
|
@ -166,6 +167,7 @@ func (q *Queries) GetAllWallets(ctx context.Context) ([]Wallet, error) {
|
||||||
&i.IsActive,
|
&i.IsActive,
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
|
&i.Currency,
|
||||||
&i.BonusBalance,
|
&i.BonusBalance,
|
||||||
&i.CashBalance,
|
&i.CashBalance,
|
||||||
); err != nil {
|
); err != nil {
|
||||||
|
|
@ -225,7 +227,7 @@ func (q *Queries) GetCustomerWallet(ctx context.Context, customerID int64) (GetC
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetWalletByID = `-- name: GetWalletByID :one
|
const GetWalletByID = `-- name: GetWalletByID :one
|
||||||
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, bonus_balance, cash_balance
|
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, currency, bonus_balance, cash_balance
|
||||||
FROM wallets
|
FROM wallets
|
||||||
WHERE id = $1
|
WHERE id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -243,6 +245,7 @@ func (q *Queries) GetWalletByID(ctx context.Context, id int64) (Wallet, error) {
|
||||||
&i.IsActive,
|
&i.IsActive,
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
|
&i.Currency,
|
||||||
&i.BonusBalance,
|
&i.BonusBalance,
|
||||||
&i.CashBalance,
|
&i.CashBalance,
|
||||||
)
|
)
|
||||||
|
|
@ -250,7 +253,7 @@ func (q *Queries) GetWalletByID(ctx context.Context, id int64) (Wallet, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const GetWalletByUserID = `-- name: GetWalletByUserID :many
|
const GetWalletByUserID = `-- name: GetWalletByUserID :many
|
||||||
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, bonus_balance, cash_balance
|
SELECT id, balance, is_withdraw, is_bettable, is_transferable, user_id, is_active, created_at, updated_at, currency, bonus_balance, cash_balance
|
||||||
FROM wallets
|
FROM wallets
|
||||||
WHERE user_id = $1
|
WHERE user_id = $1
|
||||||
`
|
`
|
||||||
|
|
@ -274,6 +277,7 @@ func (q *Queries) GetWalletByUserID(ctx context.Context, userID int64) ([]Wallet
|
||||||
&i.IsActive,
|
&i.IsActive,
|
||||||
&i.CreatedAt,
|
&i.CreatedAt,
|
||||||
&i.UpdatedAt,
|
&i.UpdatedAt,
|
||||||
|
&i.Currency,
|
||||||
&i.BonusBalance,
|
&i.BonusBalance,
|
||||||
&i.CashBalance,
|
&i.CashBalance,
|
||||||
); err != nil {
|
); err != nil {
|
||||||
|
|
|
||||||
8
go.mod
8
go.mod
|
|
@ -78,6 +78,12 @@ require (
|
||||||
)
|
)
|
||||||
|
|
||||||
require (
|
require (
|
||||||
github.com/go-resty/resty/v2 v2.16.5 // indirect
|
github.com/go-resty/resty/v2 v2.16.5
|
||||||
|
github.com/twilio/twilio-go v1.26.3
|
||||||
|
)
|
||||||
|
|
||||||
|
require (
|
||||||
|
github.com/golang/mock v1.6.0 // indirect
|
||||||
|
github.com/pkg/errors v0.9.1 // indirect
|
||||||
go.uber.org/atomic v1.9.0 // indirect
|
go.uber.org/atomic v1.9.0 // indirect
|
||||||
)
|
)
|
||||||
|
|
|
||||||
17
go.sum
17
go.sum
|
|
@ -9,6 +9,7 @@ github.com/amanuelabay/afrosms-go v1.0.6/go.mod h1:5mzzZtWSCDdvQsA0OyYf5CtbdGpl9
|
||||||
github.com/andybalholm/brotli v1.0.4/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig=
|
github.com/andybalholm/brotli v1.0.4/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig=
|
||||||
github.com/andybalholm/brotli v1.1.1 h1:PR2pgnyFznKEugtsUo0xLdDop5SKXd5Qf5ysW+7XdTA=
|
github.com/andybalholm/brotli v1.1.1 h1:PR2pgnyFznKEugtsUo0xLdDop5SKXd5Qf5ysW+7XdTA=
|
||||||
github.com/andybalholm/brotli v1.1.1/go.mod h1:05ib4cKhjx3OQYUY22hTVd34Bc8upXjOLL2rKwwZBoA=
|
github.com/andybalholm/brotli v1.1.1/go.mod h1:05ib4cKhjx3OQYUY22hTVd34Bc8upXjOLL2rKwwZBoA=
|
||||||
|
github.com/beevik/etree v1.1.0/go.mod h1:r8Aw8JqVegEf0w2fDnATrX9VpkMcyFeM0FhwO62wh+A=
|
||||||
github.com/bytedance/sonic v1.13.2 h1:8/H1FempDZqC4VqjptGo14QQlJx8VdZJegxs6wwfqpQ=
|
github.com/bytedance/sonic v1.13.2 h1:8/H1FempDZqC4VqjptGo14QQlJx8VdZJegxs6wwfqpQ=
|
||||||
github.com/bytedance/sonic v1.13.2/go.mod h1:o68xyaF9u2gvVBuGHPlUVCy+ZfmNNO5ETf1+KgkJhz4=
|
github.com/bytedance/sonic v1.13.2/go.mod h1:o68xyaF9u2gvVBuGHPlUVCy+ZfmNNO5ETf1+KgkJhz4=
|
||||||
github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU=
|
github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU=
|
||||||
|
|
@ -56,6 +57,8 @@ github.com/gofiber/fiber/v2 v2.52.6 h1:Rfp+ILPiYSvvVuIPvxrBns+HJp8qGLDnLJawAu27X
|
||||||
github.com/gofiber/fiber/v2 v2.52.6/go.mod h1:YEcBbO/FB+5M1IZNBP9FO3J9281zgPAreiI1oqg8nDw=
|
github.com/gofiber/fiber/v2 v2.52.6/go.mod h1:YEcBbO/FB+5M1IZNBP9FO3J9281zgPAreiI1oqg8nDw=
|
||||||
github.com/golang-jwt/jwt/v5 v5.2.2 h1:Rl4B7itRWVtYIHFrSNd7vhTiz9UpLdi6gZhZ3wEeDy8=
|
github.com/golang-jwt/jwt/v5 v5.2.2 h1:Rl4B7itRWVtYIHFrSNd7vhTiz9UpLdi6gZhZ3wEeDy8=
|
||||||
github.com/golang-jwt/jwt/v5 v5.2.2/go.mod h1:pqrtFR0X4osieyHYxtmOUWsAWrfe1Q5UVIyoH402zdk=
|
github.com/golang-jwt/jwt/v5 v5.2.2/go.mod h1:pqrtFR0X4osieyHYxtmOUWsAWrfe1Q5UVIyoH402zdk=
|
||||||
|
github.com/golang/mock v1.6.0 h1:ErTB+efbowRARo13NNdxyJji2egdxLGQhRaY+DUumQc=
|
||||||
|
github.com/golang/mock v1.6.0/go.mod h1:p6yTPP+5HYm5mzsMV8JkE6ZKdX+/wYM6Hr+LicevLPs=
|
||||||
github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM=
|
github.com/golang/snappy v0.0.4 h1:yAGX7huGHXlcLOEtBnF4w7FQwA26wojNCwOYAEhLjQM=
|
||||||
github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
|
github.com/golang/snappy v0.0.4/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
|
||||||
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
|
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
|
||||||
|
|
@ -96,6 +99,8 @@ github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
|
||||||
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
|
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
|
||||||
github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ=
|
github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ=
|
||||||
github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI=
|
github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI=
|
||||||
|
github.com/localtunnel/go-localtunnel v0.0.0-20170326223115-8a804488f275 h1:IZycmTpoUtQK3PD60UYBwjaCUHUP7cML494ao9/O8+Q=
|
||||||
|
github.com/localtunnel/go-localtunnel v0.0.0-20170326223115-8a804488f275/go.mod h1:zt6UU74K6Z6oMOYJbJzYpYucqdcQwSMPBEdSvGiaUMw=
|
||||||
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
||||||
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
||||||
github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
|
github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
|
||||||
|
|
@ -116,6 +121,8 @@ github.com/otiai10/curr v1.0.0/go.mod h1:LskTG5wDwr8Rs+nNQ+1LlxRjAtTZZjtJW4rMXl6
|
||||||
github.com/otiai10/mint v1.3.0/go.mod h1:F5AjcsTsWUqX+Na9fpHb52P8pcRX2CI6A3ctIT91xUo=
|
github.com/otiai10/mint v1.3.0/go.mod h1:F5AjcsTsWUqX+Na9fpHb52P8pcRX2CI6A3ctIT91xUo=
|
||||||
github.com/otiai10/mint v1.3.3/go.mod h1:/yxELlJQ0ufhjUwhshSj+wFjZ78CnZ48/1wtmBH1OTc=
|
github.com/otiai10/mint v1.3.3/go.mod h1:/yxELlJQ0ufhjUwhshSj+wFjZ78CnZ48/1wtmBH1OTc=
|
||||||
github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA=
|
github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA=
|
||||||
|
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
|
||||||
|
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||||
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||||
github.com/resend/resend-go/v2 v2.20.0 h1:MrIrgV0aHhwRgmcRPw33Nexn6aGJvCvG2XwfFpAMBGM=
|
github.com/resend/resend-go/v2 v2.20.0 h1:MrIrgV0aHhwRgmcRPw33Nexn6aGJvCvG2XwfFpAMBGM=
|
||||||
|
|
@ -152,6 +159,8 @@ github.com/swaggo/files v0.0.0-20220610200504-28940afbdbfe/go.mod h1:lKJPbtWzJ9J
|
||||||
github.com/swaggo/swag v1.8.1/go.mod h1:ugemnJsPZm/kRwFUnzBlbHRd0JY9zE1M4F+uy2pAaPQ=
|
github.com/swaggo/swag v1.8.1/go.mod h1:ugemnJsPZm/kRwFUnzBlbHRd0JY9zE1M4F+uy2pAaPQ=
|
||||||
github.com/swaggo/swag v1.16.4 h1:clWJtd9LStiG3VeijiCfOVODP6VpHtKdQy9ELFG3s1A=
|
github.com/swaggo/swag v1.16.4 h1:clWJtd9LStiG3VeijiCfOVODP6VpHtKdQy9ELFG3s1A=
|
||||||
github.com/swaggo/swag v1.16.4/go.mod h1:VBsHJRsDvfYvqoiMKnsdwhNV9LEMHgEDZcyVYX0sxPg=
|
github.com/swaggo/swag v1.16.4/go.mod h1:VBsHJRsDvfYvqoiMKnsdwhNV9LEMHgEDZcyVYX0sxPg=
|
||||||
|
github.com/twilio/twilio-go v1.26.3 h1:K2mYBzbhPVyWF+Jq5Sw53edBFvkgWo4sKTvgaO7461I=
|
||||||
|
github.com/twilio/twilio-go v1.26.3/go.mod h1:FpgNWMoD8CFnmukpKq9RNpUSGXC0BwnbeKZj2YHlIkw=
|
||||||
github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI=
|
github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI=
|
||||||
github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08=
|
github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08=
|
||||||
github.com/urfave/cli/v2 v2.3.0/go.mod h1:LJmUH05zAU44vOAcrfzZQKsZbVcdbOG8rtL3/XcUArI=
|
github.com/urfave/cli/v2 v2.3.0/go.mod h1:LJmUH05zAU44vOAcrfzZQKsZbVcdbOG8rtL3/XcUArI=
|
||||||
|
|
@ -172,13 +181,13 @@ github.com/xyproto/randomstring v1.0.5 h1:YtlWPoRdgMu3NZtP45drfy1GKoojuR7hmRcnhZ
|
||||||
github.com/xyproto/randomstring v1.0.5/go.mod h1:rgmS5DeNXLivK7YprL0pY+lTuhNQW3iGxZ18UQApw/E=
|
github.com/xyproto/randomstring v1.0.5/go.mod h1:rgmS5DeNXLivK7YprL0pY+lTuhNQW3iGxZ18UQApw/E=
|
||||||
github.com/youmark/pkcs8 v0.0.0-20240726163527-a2c0da244d78 h1:ilQV1hzziu+LLM3zUTJ0trRztfwgjqKnBWNtSRkbmwM=
|
github.com/youmark/pkcs8 v0.0.0-20240726163527-a2c0da244d78 h1:ilQV1hzziu+LLM3zUTJ0trRztfwgjqKnBWNtSRkbmwM=
|
||||||
github.com/youmark/pkcs8 v0.0.0-20240726163527-a2c0da244d78/go.mod h1:aL8wCCfTfSfmXjznFBSZNN13rSJjlIOI1fUNAtF7rmI=
|
github.com/youmark/pkcs8 v0.0.0-20240726163527-a2c0da244d78/go.mod h1:aL8wCCfTfSfmXjznFBSZNN13rSJjlIOI1fUNAtF7rmI=
|
||||||
|
github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||||
github.com/yuin/goldmark v1.4.0/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
github.com/yuin/goldmark v1.4.0/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||||
github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
|
github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
|
||||||
go.mongodb.org/mongo-driver v1.17.3 h1:TQyXhnsWfWtgAhMtOgtYHMTkZIfBTpMTsMnd9ZBeHxQ=
|
go.mongodb.org/mongo-driver v1.17.3 h1:TQyXhnsWfWtgAhMtOgtYHMTkZIfBTpMTsMnd9ZBeHxQ=
|
||||||
go.mongodb.org/mongo-driver v1.17.3/go.mod h1:Hy04i7O2kC4RS06ZrhPRqj/u4DTYkFDAAccj+rVKqgQ=
|
go.mongodb.org/mongo-driver v1.17.3/go.mod h1:Hy04i7O2kC4RS06ZrhPRqj/u4DTYkFDAAccj+rVKqgQ=
|
||||||
go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE=
|
go.uber.org/atomic v1.9.0 h1:ECmE8Bn/WFTYwEW/bpKD3M8VtR/zQVbavAoalC1PYyE=
|
||||||
go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
|
go.uber.org/atomic v1.9.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
|
||||||
go.uber.org/atomic v1.11.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0=
|
|
||||||
go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto=
|
go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto=
|
||||||
go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE=
|
go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE=
|
||||||
go.uber.org/multierr v1.10.0 h1:S0h4aNzvfcFsC3dRF1jLoaov7oRaKqRGC/pUEJ2yvPQ=
|
go.uber.org/multierr v1.10.0 h1:S0h4aNzvfcFsC3dRF1jLoaov7oRaKqRGC/pUEJ2yvPQ=
|
||||||
|
|
@ -201,6 +210,7 @@ golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn
|
||||||
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||||
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s=
|
||||||
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||||
|
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
|
||||||
golang.org/x/net v0.0.0-20210421230115-4e50805a0758/go.mod h1:72T/g9IO56b78aLF+1Kcs5dz7/ng1VjMUvfKvpfy+jM=
|
golang.org/x/net v0.0.0-20210421230115-4e50805a0758/go.mod h1:72T/g9IO56b78aLF+1Kcs5dz7/ng1VjMUvfKvpfy+jM=
|
||||||
golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20210805182204-aaa1db679c0d/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
|
|
@ -216,8 +226,10 @@ golang.org/x/sync v0.12.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
|
||||||
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
|
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210420072515-93ed5bcd2bfe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210420072515-93ed5bcd2bfe/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
|
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20210809222454-d867a43fc93e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20211216021012-1d35b9e2eb4e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
|
|
@ -236,9 +248,12 @@ golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
||||||
golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ=
|
golang.org/x/text v0.3.8/go.mod h1:E6s5w1FMmriuDzIBO73fBruAKo1PCIq6d2Q6DHfQ8WQ=
|
||||||
golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY=
|
golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY=
|
||||||
golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4=
|
golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4=
|
||||||
|
golang.org/x/time v0.6.0 h1:eTDhh4ZXt5Qf0augr54TN6suAUudPcawVZeIAPU7D4U=
|
||||||
|
golang.org/x/time v0.6.0/go.mod h1:3BpzKBy/shNhVucY/MWOyx10tF3SFh9QdLuxbVysPQM=
|
||||||
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||||
golang.org/x/tools v0.0.0-20190328211700-ab21143f2384/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
|
golang.org/x/tools v0.0.0-20190328211700-ab21143f2384/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs=
|
||||||
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
|
golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo=
|
||||||
|
golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
||||||
golang.org/x/tools v0.1.7/go.mod h1:LGqMHiF4EqQNHR1JncWGqT5BVaXmza+X+BDGol+dOxo=
|
golang.org/x/tools v0.1.7/go.mod h1:LGqMHiF4EqQNHR1JncWGqT5BVaXmza+X+BDGol+dOxo=
|
||||||
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
|
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
|
||||||
golang.org/x/tools v0.31.0 h1:0EedkvKDbh+qistFTd0Bcwe/YLh4vHwWEkiI0toFIBU=
|
golang.org/x/tools v0.31.0 h1:0EedkvKDbh+qistFTd0Bcwe/YLh4vHwWEkiI0toFIBU=
|
||||||
|
|
|
||||||
|
|
@ -13,25 +13,28 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
ErrInvalidDbUrl = errors.New("db url is invalid")
|
ErrInvalidDbUrl = errors.New("db url is invalid")
|
||||||
ErrInvalidPort = errors.New("port number is invalid")
|
ErrInvalidPort = errors.New("port number is invalid")
|
||||||
ErrRefreshExpiry = errors.New("refresh token expiry is invalid")
|
ErrRefreshExpiry = errors.New("refresh token expiry is invalid")
|
||||||
ErrAccessExpiry = errors.New("access token expiry is invalid")
|
ErrAccessExpiry = errors.New("access token expiry is invalid")
|
||||||
ErrInvalidJwtKey = errors.New("jwt key is invalid")
|
ErrInvalidJwtKey = errors.New("jwt key is invalid")
|
||||||
ErrLogLevel = errors.New("log level not set")
|
ErrLogLevel = errors.New("log level not set")
|
||||||
ErrInvalidLevel = errors.New("invalid log level")
|
ErrInvalidLevel = errors.New("invalid log level")
|
||||||
ErrInvalidEnv = errors.New("env not set or invalid")
|
ErrInvalidEnv = errors.New("env not set or invalid")
|
||||||
ErrInvalidSMSAPIKey = errors.New("SMS API key is invalid")
|
ErrInvalidSMSAPIKey = errors.New("SMS API key is invalid")
|
||||||
ErrMissingBetToken = errors.New("missing BET365_TOKEN in .env")
|
ErrMissingBetToken = errors.New("missing BET365_TOKEN in .env")
|
||||||
ErrInvalidPopOKClientID = errors.New("PopOK client ID is invalid")
|
ErrInvalidPopOKClientID = errors.New("PopOK client ID is invalid")
|
||||||
ErrInvalidPopOKSecretKey = errors.New("PopOK secret key is invalid")
|
ErrInvalidPopOKSecretKey = errors.New("PopOK secret key is invalid")
|
||||||
ErrInvalidPopOKBaseURL = errors.New("PopOK base URL is invalid")
|
ErrInvalidPopOKBaseURL = errors.New("PopOK base URL is invalid")
|
||||||
ErrInvalidPopOKCallbackURL = errors.New("PopOK callback URL is invalid")
|
ErrInvalidPopOKCallbackURL = errors.New("PopOK callback URL is invalid")
|
||||||
ErrInvalidVeliAPIURL = errors.New("Veli API URL is invalid")
|
ErrInvalidVeliAPIURL = errors.New("Veli API URL is invalid")
|
||||||
ErrInvalidVeliOperatorKey = errors.New("Veli operator key is invalid")
|
ErrInvalidVeliOperatorKey = errors.New("Veli operator key is invalid")
|
||||||
ErrInvalidVeliSecretKey = errors.New("Veli secret key is invalid")
|
ErrInvalidVeliSecretKey = errors.New("Veli secret key is invalid")
|
||||||
ErrMissingResendApiKey = errors.New("missing Resend Api key")
|
ErrMissingResendApiKey = errors.New("missing Resend Api key")
|
||||||
ErrMissingResendSenderEmail = errors.New("missing Resend sender name")
|
ErrMissingResendSenderEmail = errors.New("missing Resend sender name")
|
||||||
|
ErrMissingTwilioAccountSid = errors.New("missing twilio account sid")
|
||||||
|
ErrMissingTwilioAuthToken = errors.New("missing twilio auth token")
|
||||||
|
ErrMissingTwilioSenderPhoneNumber = errors.New("missing twilio sender phone number")
|
||||||
)
|
)
|
||||||
|
|
||||||
type AleaPlayConfig struct {
|
type AleaPlayConfig struct {
|
||||||
|
|
@ -85,6 +88,9 @@ type Config struct {
|
||||||
VeliGames VeliConfig `mapstructure:"veli_games"`
|
VeliGames VeliConfig `mapstructure:"veli_games"`
|
||||||
ResendApiKey string
|
ResendApiKey string
|
||||||
ResendSenderEmail string
|
ResendSenderEmail string
|
||||||
|
TwilioAccountSid string
|
||||||
|
TwilioAuthToken string
|
||||||
|
TwilioSenderPhoneNumber string
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewConfig() (*Config, error) {
|
func NewConfig() (*Config, error) {
|
||||||
|
|
@ -324,6 +330,24 @@ func (c *Config) loadEnv() error {
|
||||||
}
|
}
|
||||||
c.ResendSenderEmail = resendSenderEmail
|
c.ResendSenderEmail = resendSenderEmail
|
||||||
|
|
||||||
|
twilioAccountSid := os.Getenv("TWILIO_ACCOUNT_SID")
|
||||||
|
if twilioAccountSid == "" {
|
||||||
|
return ErrMissingTwilioAccountSid
|
||||||
|
}
|
||||||
|
c.TwilioAccountSid = twilioAccountSid
|
||||||
|
|
||||||
|
twilioAuthToken := os.Getenv("TWILIO_AUTH_TOKEN")
|
||||||
|
if twilioAuthToken == "" {
|
||||||
|
return ErrMissingTwilioAuthToken
|
||||||
|
}
|
||||||
|
c.TwilioAuthToken = twilioAuthToken
|
||||||
|
|
||||||
|
twilioSenderPhoneNumber := os.Getenv("TWILIO_SENDER_PHONE_NUMBER")
|
||||||
|
if twilioSenderPhoneNumber == "" {
|
||||||
|
return ErrMissingTwilioSenderPhoneNumber
|
||||||
|
}
|
||||||
|
c.TwilioSenderPhoneNumber = twilioSenderPhoneNumber
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -80,16 +80,17 @@ type GetBet struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
type CreateBet struct {
|
type CreateBet struct {
|
||||||
Amount Currency
|
Amount Currency
|
||||||
TotalOdds float32
|
TotalOdds float32
|
||||||
Status OutcomeStatus
|
Status OutcomeStatus
|
||||||
FullName string
|
FullName string
|
||||||
PhoneNumber string
|
PhoneNumber string
|
||||||
CompanyID ValidInt64 // Can Be Nullable
|
CompanyID ValidInt64 // Can Be Nullable
|
||||||
BranchID ValidInt64 // Can Be Nullable
|
BranchID ValidInt64 // Can Be Nullable
|
||||||
UserID ValidInt64 // Can Be Nullable
|
UserID ValidInt64 // Can Be Nullable
|
||||||
IsShopBet bool
|
IsShopBet bool
|
||||||
CashoutID string
|
CashoutID string
|
||||||
|
OutcomesHash string
|
||||||
}
|
}
|
||||||
|
|
||||||
type CreateBetOutcomeReq struct {
|
type CreateBetOutcomeReq struct {
|
||||||
|
|
@ -173,4 +174,3 @@ func ConvertBet(bet GetBet) BetRes {
|
||||||
CreatedAt: bet.CreatedAt,
|
CreatedAt: bet.CreatedAt,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -53,6 +53,7 @@ type UpdateBranch struct {
|
||||||
BranchManagerID *int64
|
BranchManagerID *int64
|
||||||
CompanyID *int64
|
CompanyID *int64
|
||||||
IsSelfOwned *bool
|
IsSelfOwned *bool
|
||||||
|
IsActive *bool
|
||||||
}
|
}
|
||||||
|
|
||||||
type CreateSupportedOperation struct {
|
type CreateSupportedOperation struct {
|
||||||
|
|
|
||||||
|
|
@ -26,6 +26,13 @@ const (
|
||||||
OtpMediumSms OtpMedium = "sms"
|
OtpMediumSms OtpMedium = "sms"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
type OtpProvider string
|
||||||
|
|
||||||
|
const (
|
||||||
|
TwilioSms OtpProvider = "twilio"
|
||||||
|
AfroMessage OtpProvider = "aformessage"
|
||||||
|
)
|
||||||
|
|
||||||
type Otp struct {
|
type Otp struct {
|
||||||
ID int64
|
ID int64
|
||||||
SentTo string
|
SentTo string
|
||||||
|
|
|
||||||
|
|
@ -265,6 +265,19 @@ func (s *Store) GetBetByUserID(ctx context.Context, UserID int64) ([]domain.GetB
|
||||||
return result, nil
|
return result, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *Store) GetBetCount(ctx context.Context, UserID int64, outcomesHash string) (int64, error) {
|
||||||
|
count, err := s.queries.GetBetCount(ctx, dbgen.GetBetCountParams{
|
||||||
|
UserID: pgtype.Int8{Int64: UserID},
|
||||||
|
OutcomesHash: outcomesHash,
|
||||||
|
})
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return count, nil
|
||||||
|
}
|
||||||
|
|
||||||
func (s *Store) UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error {
|
func (s *Store) UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error {
|
||||||
err := s.queries.UpdateCashOut(ctx, dbgen.UpdateCashOutParams{
|
err := s.queries.UpdateCashOut(ctx, dbgen.UpdateCashOutParams{
|
||||||
ID: id,
|
ID: id,
|
||||||
|
|
|
||||||
|
|
@ -83,6 +83,12 @@ func convertUpdateBranch(updateBranch domain.UpdateBranch) dbgen.UpdateBranchPar
|
||||||
Valid: true,
|
Valid: true,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if updateBranch.IsActive != nil {
|
||||||
|
newUpdateBranch.IsActive = pgtype.Bool{
|
||||||
|
Bool: *updateBranch.IsActive,
|
||||||
|
Valid: true,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return newUpdateBranch
|
return newUpdateBranch
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@ type BetStore interface {
|
||||||
GetBetByUserID(ctx context.Context, UserID int64) ([]domain.GetBet, error)
|
GetBetByUserID(ctx context.Context, UserID int64) ([]domain.GetBet, error)
|
||||||
GetBetOutcomeByEventID(ctx context.Context, eventID int64) ([]domain.BetOutcome, error)
|
GetBetOutcomeByEventID(ctx context.Context, eventID int64) ([]domain.BetOutcome, error)
|
||||||
GetBetOutcomeByBetID(ctx context.Context, betID int64) ([]domain.BetOutcome, error)
|
GetBetOutcomeByBetID(ctx context.Context, betID int64) ([]domain.BetOutcome, error)
|
||||||
|
GetBetCount(ctx context.Context, userID int64, outcomesHash string) (int64, error)
|
||||||
UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error
|
UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error
|
||||||
UpdateStatus(ctx context.Context, id int64, status domain.OutcomeStatus) error
|
UpdateStatus(ctx context.Context, id int64, status domain.OutcomeStatus) error
|
||||||
UpdateBetOutcomeStatus(ctx context.Context, id int64, status domain.OutcomeStatus) (domain.BetOutcome, error)
|
UpdateBetOutcomeStatus(ctx context.Context, id int64, status domain.OutcomeStatus) (domain.BetOutcome, error)
|
||||||
|
|
|
||||||
|
|
@ -3,13 +3,17 @@ package bet
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"crypto/rand"
|
"crypto/rand"
|
||||||
|
"crypto/sha256"
|
||||||
|
"encoding/hex"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log/slog"
|
"log/slog"
|
||||||
"math/big"
|
"math/big"
|
||||||
random "math/rand"
|
random "math/rand"
|
||||||
|
"sort"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
||||||
|
|
@ -196,6 +200,7 @@ func (s *Service) PlaceBet(ctx context.Context, req domain.CreateBetReq, userID
|
||||||
var totalOdds float32 = 1
|
var totalOdds float32 = 1
|
||||||
|
|
||||||
for _, outcomeReq := range req.Outcomes {
|
for _, outcomeReq := range req.Outcomes {
|
||||||
|
fmt.Println("reqq: ", outcomeReq)
|
||||||
newOutcome, err := s.GenerateBetOutcome(ctx, outcomeReq.EventID, outcomeReq.MarketID, outcomeReq.OddID)
|
newOutcome, err := s.GenerateBetOutcome(ctx, outcomeReq.EventID, outcomeReq.MarketID, outcomeReq.OddID)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
s.mongoLogger.Error("failed to generate outcome",
|
s.mongoLogger.Error("failed to generate outcome",
|
||||||
|
|
@ -211,6 +216,23 @@ func (s *Service) PlaceBet(ctx context.Context, req domain.CreateBetReq, userID
|
||||||
outcomes = append(outcomes, newOutcome)
|
outcomes = append(outcomes, newOutcome)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
outcomesHash, err := generateOutcomeHash(outcomes)
|
||||||
|
if err != nil {
|
||||||
|
s.mongoLogger.Error("failed to generate outcome hash",
|
||||||
|
zap.Int64("user_id", userID),
|
||||||
|
zap.Error(err),
|
||||||
|
)
|
||||||
|
return domain.CreateBetRes{}, err
|
||||||
|
}
|
||||||
|
|
||||||
|
count, err := s.GetBetCount(ctx, userID, outcomesHash)
|
||||||
|
if err != nil {
|
||||||
|
return domain.CreateBetRes{}, err
|
||||||
|
}
|
||||||
|
if count == 2 {
|
||||||
|
return domain.CreateBetRes{}, fmt.Errorf("bet already pleaced twice")
|
||||||
|
}
|
||||||
|
|
||||||
cashoutID, err := s.GenerateCashoutID()
|
cashoutID, err := s.GenerateCashoutID()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
s.mongoLogger.Error("failed to generate cashout ID",
|
s.mongoLogger.Error("failed to generate cashout ID",
|
||||||
|
|
@ -221,12 +243,13 @@ func (s *Service) PlaceBet(ctx context.Context, req domain.CreateBetReq, userID
|
||||||
}
|
}
|
||||||
|
|
||||||
newBet := domain.CreateBet{
|
newBet := domain.CreateBet{
|
||||||
Amount: domain.ToCurrency(req.Amount),
|
Amount: domain.ToCurrency(req.Amount),
|
||||||
TotalOdds: totalOdds,
|
TotalOdds: totalOdds,
|
||||||
Status: req.Status,
|
Status: req.Status,
|
||||||
FullName: req.FullName,
|
FullName: req.FullName,
|
||||||
PhoneNumber: req.PhoneNumber,
|
PhoneNumber: req.PhoneNumber,
|
||||||
CashoutID: cashoutID,
|
CashoutID: cashoutID,
|
||||||
|
OutcomesHash: outcomesHash,
|
||||||
}
|
}
|
||||||
|
|
||||||
switch role {
|
switch role {
|
||||||
|
|
@ -321,6 +344,7 @@ func (s *Service) PlaceBet(ctx context.Context, req domain.CreateBetReq, userID
|
||||||
return domain.CreateBetRes{}, fmt.Errorf("Unknown Role Type")
|
return domain.CreateBetRes{}, fmt.Errorf("Unknown Role Type")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fmt.Println("Bet is: ", newBet)
|
||||||
bet, err := s.CreateBet(ctx, newBet)
|
bet, err := s.CreateBet(ctx, newBet)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
s.mongoLogger.Error("failed to create bet",
|
s.mongoLogger.Error("failed to create bet",
|
||||||
|
|
@ -636,6 +660,10 @@ func (s *Service) GetBetByUserID(ctx context.Context, UserID int64) ([]domain.Ge
|
||||||
return s.betStore.GetBetByUserID(ctx, UserID)
|
return s.betStore.GetBetByUserID(ctx, UserID)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *Service) GetBetCount(ctx context.Context, UserID int64, outcomesHash string) (int64, error) {
|
||||||
|
return s.betStore.GetBetCount(ctx, UserID, outcomesHash)
|
||||||
|
}
|
||||||
|
|
||||||
func (s *Service) UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error {
|
func (s *Service) UpdateCashOut(ctx context.Context, id int64, cashedOut bool) error {
|
||||||
return s.betStore.UpdateCashOut(ctx, id, cashedOut)
|
return s.betStore.UpdateCashOut(ctx, id, cashedOut)
|
||||||
}
|
}
|
||||||
|
|
@ -785,3 +813,24 @@ func (s *Service) UpdateBetOutcomeStatus(ctx context.Context, id int64, status d
|
||||||
func (s *Service) DeleteBet(ctx context.Context, id int64) error {
|
func (s *Service) DeleteBet(ctx context.Context, id int64) error {
|
||||||
return s.betStore.DeleteBet(ctx, id)
|
return s.betStore.DeleteBet(ctx, id)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func generateOutcomeHash(outcomes []domain.CreateBetOutcome) (string, error) {
|
||||||
|
// should always be in the same order for producing the same hash
|
||||||
|
sort.Slice(outcomes, func(i, j int) bool {
|
||||||
|
if outcomes[i].EventID != outcomes[j].EventID {
|
||||||
|
return outcomes[i].EventID < outcomes[j].EventID
|
||||||
|
}
|
||||||
|
if outcomes[i].MarketID != outcomes[j].MarketID {
|
||||||
|
return outcomes[i].MarketID < outcomes[j].MarketID
|
||||||
|
}
|
||||||
|
return outcomes[i].OddID < outcomes[j].OddID
|
||||||
|
})
|
||||||
|
|
||||||
|
var sb strings.Builder
|
||||||
|
for _, o := range outcomes {
|
||||||
|
sb.WriteString(fmt.Sprintf("%d-%d-%d;", o.EventID, o.MarketID, o.OddID))
|
||||||
|
}
|
||||||
|
|
||||||
|
sum := sha256.Sum256([]byte(sb.String()))
|
||||||
|
return hex.EncodeToString(sum[:]), nil
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -10,18 +10,29 @@ import (
|
||||||
"github.com/SamuelTariku/FortuneBet-Backend/internal/pkgs/helpers"
|
"github.com/SamuelTariku/FortuneBet-Backend/internal/pkgs/helpers"
|
||||||
afro "github.com/amanuelabay/afrosms-go"
|
afro "github.com/amanuelabay/afrosms-go"
|
||||||
"github.com/resend/resend-go/v2"
|
"github.com/resend/resend-go/v2"
|
||||||
|
"github.com/twilio/twilio-go"
|
||||||
|
twilioApi "github.com/twilio/twilio-go/rest/api/v2010"
|
||||||
"golang.org/x/crypto/bcrypt"
|
"golang.org/x/crypto/bcrypt"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (s *Service) SendOtp(ctx context.Context, sentTo string, otpFor domain.OtpFor, medium domain.OtpMedium) error {
|
func (s *Service) SendOtp(ctx context.Context, sentTo string, otpFor domain.OtpFor, medium domain.OtpMedium, provider domain.OtpProvider) error {
|
||||||
otpCode := helpers.GenerateOTP()
|
otpCode := helpers.GenerateOTP()
|
||||||
|
|
||||||
message := fmt.Sprintf("Welcome to Fortune bets, your OTP is %s please don't share with anyone.", otpCode)
|
message := fmt.Sprintf("Welcome to Fortune bets, your OTP is %s please don't share with anyone.", otpCode)
|
||||||
|
|
||||||
switch medium {
|
switch medium {
|
||||||
case domain.OtpMediumSms:
|
case domain.OtpMediumSms:
|
||||||
if err := s.SendSMSOTP(ctx, sentTo, message); err != nil {
|
switch provider {
|
||||||
return err
|
case "twilio":
|
||||||
|
if err := s.SendTwilioSMSOTP(ctx, sentTo, message, provider); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
case "afromessage":
|
||||||
|
if err := s.SendAfroMessageSMSOTP(ctx, sentTo, message, provider); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("invalid sms provider: %s", provider)
|
||||||
}
|
}
|
||||||
case domain.OtpMediumEmail:
|
case domain.OtpMediumEmail:
|
||||||
if err := s.SendEmailOTP(ctx, sentTo, message); err != nil {
|
if err := s.SendEmailOTP(ctx, sentTo, message); err != nil {
|
||||||
|
|
@ -51,7 +62,7 @@ func hashPassword(plaintextPassword string) ([]byte, error) {
|
||||||
return hash, nil
|
return hash, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Service) SendSMSOTP(ctx context.Context, receiverPhone, message string) error {
|
func (s *Service) SendAfroMessageSMSOTP(ctx context.Context, receiverPhone, message string, provider domain.OtpProvider) error {
|
||||||
apiKey := s.config.AFRO_SMS_API_KEY
|
apiKey := s.config.AFRO_SMS_API_KEY
|
||||||
senderName := s.config.AFRO_SMS_SENDER_NAME
|
senderName := s.config.AFRO_SMS_SENDER_NAME
|
||||||
hostURL := s.config.ADRO_SMS_HOST_URL
|
hostURL := s.config.ADRO_SMS_HOST_URL
|
||||||
|
|
@ -79,6 +90,29 @@ func (s *Service) SendSMSOTP(ctx context.Context, receiverPhone, message string)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *Service) SendTwilioSMSOTP(ctx context.Context, receiverPhone, message string, provider domain.OtpProvider) error {
|
||||||
|
accountSid := s.config.TwilioAccountSid
|
||||||
|
authToken := s.config.TwilioAuthToken
|
||||||
|
senderPhone := s.config.TwilioSenderPhoneNumber
|
||||||
|
|
||||||
|
client := twilio.NewRestClientWithParams(twilio.ClientParams{
|
||||||
|
Username: accountSid,
|
||||||
|
Password: authToken,
|
||||||
|
})
|
||||||
|
|
||||||
|
params := &twilioApi.CreateMessageParams{}
|
||||||
|
params.SetTo(receiverPhone)
|
||||||
|
params.SetFrom(senderPhone)
|
||||||
|
params.SetBody(message)
|
||||||
|
|
||||||
|
_, err := client.Api.CreateMessage(params)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("Error sending SMS message: %s" + err.Error())
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
func (s *Service) SendEmailOTP(ctx context.Context, receiverEmail, message string) error {
|
func (s *Service) SendEmailOTP(ctx context.Context, receiverEmail, message string) error {
|
||||||
apiKey := s.config.ResendApiKey
|
apiKey := s.config.ResendApiKey
|
||||||
client := resend.NewClient(apiKey)
|
client := resend.NewClient(apiKey)
|
||||||
|
|
|
||||||
|
|
@ -10,7 +10,7 @@ import (
|
||||||
func (s *Service) CheckPhoneEmailExist(ctx context.Context, phoneNum, email string) (bool, bool, error) { // email,phone,error
|
func (s *Service) CheckPhoneEmailExist(ctx context.Context, phoneNum, email string) (bool, bool, error) { // email,phone,error
|
||||||
return s.userStore.CheckPhoneEmailExist(ctx, phoneNum, email)
|
return s.userStore.CheckPhoneEmailExist(ctx, phoneNum, email)
|
||||||
}
|
}
|
||||||
func (s *Service) SendRegisterCode(ctx context.Context, medium domain.OtpMedium, sentTo string) error {
|
func (s *Service) SendRegisterCode(ctx context.Context, medium domain.OtpMedium, sentTo string, provider domain.OtpProvider) error {
|
||||||
var err error
|
var err error
|
||||||
// check if user exists
|
// check if user exists
|
||||||
switch medium {
|
switch medium {
|
||||||
|
|
@ -26,7 +26,7 @@ func (s *Service) SendRegisterCode(ctx context.Context, medium domain.OtpMedium,
|
||||||
}
|
}
|
||||||
|
|
||||||
// send otp based on the medium
|
// send otp based on the medium
|
||||||
return s.SendOtp(ctx, sentTo, domain.OtpRegister, medium)
|
return s.SendOtp(ctx, sentTo, domain.OtpRegister, medium, provider)
|
||||||
}
|
}
|
||||||
func (s *Service) RegisterUser(ctx context.Context, registerReq domain.RegisterUserReq) (domain.User, error) { // normal
|
func (s *Service) RegisterUser(ctx context.Context, registerReq domain.RegisterUserReq) (domain.User, error) { // normal
|
||||||
// get otp
|
// get otp
|
||||||
|
|
|
||||||
|
|
@ -8,7 +8,7 @@ import (
|
||||||
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (s *Service) SendResetCode(ctx context.Context, medium domain.OtpMedium, sentTo string) error {
|
func (s *Service) SendResetCode(ctx context.Context, medium domain.OtpMedium, sentTo string, provider domain.OtpProvider) error {
|
||||||
|
|
||||||
var err error
|
var err error
|
||||||
// check if user exists
|
// check if user exists
|
||||||
|
|
@ -23,7 +23,7 @@ func (s *Service) SendResetCode(ctx context.Context, medium domain.OtpMedium, se
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
return s.SendOtp(ctx, sentTo, domain.OtpReset, medium)
|
return s.SendOtp(ctx, sentTo, domain.OtpReset, medium, provider)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -57,7 +57,7 @@ func (s *Service) ResetPassword(ctx context.Context, resetReq domain.ResetPasswo
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// reset pass and mark otp as used
|
// reset pass and mark otp as used
|
||||||
|
|
||||||
err = s.userStore.UpdatePassword(ctx, sentTo, hashedPassword, otp.ID)
|
err = s.userStore.UpdatePassword(ctx, sentTo, hashedPassword, otp.ID)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
|
|
||||||
|
|
@ -46,22 +46,22 @@ func StartDataFetchingCrons(eventService eventsvc.Service, oddsService oddssvc.S
|
||||||
spec string
|
spec string
|
||||||
task func()
|
task func()
|
||||||
}{
|
}{
|
||||||
// {
|
{
|
||||||
// spec: "0 0 * * * *", // Every 1 hour
|
spec: "0 0 * * * *", // Every 1 hour
|
||||||
// task: func() {
|
task: func() {
|
||||||
// if err := eventService.FetchUpcomingEvents(context.Background()); err != nil {
|
if err := eventService.FetchUpcomingEvents(context.Background()); err != nil {
|
||||||
// log.Printf("FetchUpcomingEvents error: %v", err)
|
log.Printf("FetchUpcomingEvents error: %v", err)
|
||||||
// }
|
}
|
||||||
// },
|
},
|
||||||
// },
|
},
|
||||||
// {
|
{
|
||||||
// spec: "0 0 * * * *", // Every 15 minutes
|
spec: "0 0 * * * *", // Every 15 minutes
|
||||||
// task: func() {
|
task: func() {
|
||||||
// if err := oddsService.FetchNonLiveOdds(context.Background()); err != nil {
|
if err := oddsService.FetchNonLiveOdds(context.Background()); err != nil {
|
||||||
// log.Printf("FetchNonLiveOdds error: %v", err)
|
log.Printf("FetchNonLiveOdds error: %v", err)
|
||||||
// }
|
}
|
||||||
// },
|
},
|
||||||
// },
|
},
|
||||||
{
|
{
|
||||||
spec: "0 */5 * * * *", // Every 5 Minutes
|
spec: "0 */5 * * * *", // Every 5 Minutes
|
||||||
task: func() {
|
task: func() {
|
||||||
|
|
@ -89,7 +89,7 @@ func StartDataFetchingCrons(eventService eventsvc.Service, oddsService oddssvc.S
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, job := range schedule {
|
for _, job := range schedule {
|
||||||
job.task()
|
// job.task()
|
||||||
if _, err := c.AddFunc(job.spec, job.task); err != nil {
|
if _, err := c.AddFunc(job.spec, job.task); err != nil {
|
||||||
log.Fatalf("Failed to schedule cron job: %v", err)
|
log.Fatalf("Failed to schedule cron job: %v", err)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -40,8 +40,7 @@ func (h *Handler) CreateBet(c *fiber.Ctx) error {
|
||||||
return response.WriteJSON(c, fiber.StatusBadRequest, "Invalid request", valErrs, nil)
|
return response.WriteJSON(c, fiber.StatusBadRequest, "Invalid request", valErrs, nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
res, err := h.betSvc.
|
res, err := h.betSvc.PlaceBet(c.Context(), req, userID, role)
|
||||||
PlaceBet(c.Context(), req, userID, role)
|
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
h.logger.Error("PlaceBet failed", "error", err)
|
h.logger.Error("PlaceBet failed", "error", err)
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@ package handlers
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"strconv"
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
|
||||||
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
"github.com/SamuelTariku/FortuneBet-Backend/internal/domain"
|
||||||
"github.com/SamuelTariku/FortuneBet-Backend/internal/services/authentication"
|
"github.com/SamuelTariku/FortuneBet-Backend/internal/services/authentication"
|
||||||
|
|
@ -682,6 +683,42 @@ func (h *Handler) UpdateBranch(c *fiber.Ctx) error {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (h *Handler) UpdateBranchStatus(c *fiber.Ctx) error {
|
||||||
|
branchID := c.Params("id")
|
||||||
|
id, err := strconv.ParseInt(branchID, 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
h.logger.Error("Invalid branch ID", "branchID", branchID, "error", err)
|
||||||
|
return response.WriteJSON(c, fiber.StatusBadRequest, "Invalid branch ID", err, nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
var isActive bool
|
||||||
|
path := strings.Split(strings.Trim(c.Path(), "/"), "/")
|
||||||
|
|
||||||
|
if path[len(path)-1] == "set-active" {
|
||||||
|
isActive = true
|
||||||
|
} else if path[len(path)-1] == "set-inactive" {
|
||||||
|
isActive = false
|
||||||
|
} else {
|
||||||
|
h.logger.Error("Invalid branch status", "status", isActive, "error", err)
|
||||||
|
return response.WriteJSON(c, fiber.StatusBadRequest, "Invalid branch status", err, nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
branch, err := h.branchSvc.UpdateBranch(c.Context(), domain.UpdateBranch{
|
||||||
|
ID: id,
|
||||||
|
IsActive: &isActive,
|
||||||
|
})
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
h.logger.Error("Failed to update branch", "branchID", id, "error", err)
|
||||||
|
return response.WriteJSON(c, fiber.StatusInternalServerError, "Failed to update branch", err, nil)
|
||||||
|
}
|
||||||
|
|
||||||
|
res := convertBranch(branch)
|
||||||
|
|
||||||
|
return response.WriteJSON(c, fiber.StatusOK, "Branch Updated", res, nil)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
// DeleteBranch godoc
|
// DeleteBranch godoc
|
||||||
// @Summary Delete the branch
|
// @Summary Delete the branch
|
||||||
// @Description Delete the branch
|
// @Description Delete the branch
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ import (
|
||||||
|
|
||||||
func GetLogsHandler(appCtx context.Context) fiber.Handler {
|
func GetLogsHandler(appCtx context.Context) fiber.Handler {
|
||||||
return func(c *fiber.Ctx) error {
|
return func(c *fiber.Ctx) error {
|
||||||
client, err := mongo.Connect(appCtx, options.Client().ApplyURI("mongodb://root:secret@mongo:27017/?authSource=admin"))
|
client, err := mongo.Connect(appCtx, options.Client().ApplyURI("mongodb://root:secret@localhost:27017/?authSource=admin"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, "MongoDB connection failed: "+err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, "MongoDB connection failed: "+err.Error())
|
||||||
}
|
}
|
||||||
|
|
@ -32,7 +32,6 @@ func GetLogsHandler(appCtx context.Context) fiber.Handler {
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, "Cursor decoding error: "+err.Error())
|
return fiber.NewError(fiber.StatusInternalServerError, "Cursor decoding error: "+err.Error())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return c.JSON(logs)
|
return c.JSON(logs)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -59,8 +59,9 @@ func (h *Handler) CheckPhoneEmailExist(c *fiber.Ctx) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
type RegisterCodeReq struct {
|
type RegisterCodeReq struct {
|
||||||
Email string `json:"email" example:"john.doe@example.com"`
|
Email string `json:"email" example:"john.doe@example.com"`
|
||||||
PhoneNumber string `json:"phone_number" example:"1234567890"`
|
PhoneNumber string `json:"phone_number" example:"1234567890"`
|
||||||
|
Provider domain.OtpProvider `json:"provider" validate:"required" example:"twilio"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// SendRegisterCode godoc
|
// SendRegisterCode godoc
|
||||||
|
|
@ -98,7 +99,7 @@ func (h *Handler) SendRegisterCode(c *fiber.Ctx) error {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, "Email or PhoneNumber must be provided")
|
return fiber.NewError(fiber.StatusBadRequest, "Email or PhoneNumber must be provided")
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := h.userSvc.SendRegisterCode(c.Context(), medium, sentTo); err != nil {
|
if err := h.userSvc.SendRegisterCode(c.Context(), medium, sentTo, req.Provider); err != nil {
|
||||||
h.logger.Error("Failed to send register code", "error", err)
|
h.logger.Error("Failed to send register code", "error", err)
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, "Failed to send register code")
|
return fiber.NewError(fiber.StatusInternalServerError, "Failed to send register code")
|
||||||
}
|
}
|
||||||
|
|
@ -107,13 +108,14 @@ func (h *Handler) SendRegisterCode(c *fiber.Ctx) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
type RegisterUserReq struct {
|
type RegisterUserReq struct {
|
||||||
FirstName string `json:"first_name" example:"John"`
|
FirstName string `json:"first_name" example:"John"`
|
||||||
LastName string `json:"last_name" example:"Doe"`
|
LastName string `json:"last_name" example:"Doe"`
|
||||||
Email string `json:"email" example:"john.doe@example.com"`
|
Email string `json:"email" example:"john.doe@example.com"`
|
||||||
PhoneNumber string `json:"phone_number" example:"1234567890"`
|
PhoneNumber string `json:"phone_number" example:"1234567890"`
|
||||||
Password string `json:"password" example:"password123"`
|
Password string `json:"password" example:"password123"`
|
||||||
Otp string `json:"otp" example:"123456"`
|
Otp string `json:"otp" example:"123456"`
|
||||||
ReferalCode string `json:"referal_code" example:"ABC123"`
|
ReferalCode string `json:"referal_code" example:"ABC123"`
|
||||||
|
Provider domain.OtpProvider `json:"provider" validate:"required" example:"twilio"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// RegisterUser godoc
|
// RegisterUser godoc
|
||||||
|
|
@ -203,8 +205,9 @@ func (h *Handler) RegisterUser(c *fiber.Ctx) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
type ResetCodeReq struct {
|
type ResetCodeReq struct {
|
||||||
Email string `json:"email" example:"john.doe@example.com"`
|
Email string `json:"email" example:"john.doe@example.com"`
|
||||||
PhoneNumber string `json:"phone_number" validate:"required_without=Email" example:"1234567890"`
|
PhoneNumber string `json:"phone_number" validate:"required_without=Email" example:"1234567890"`
|
||||||
|
Provider domain.OtpProvider `json:"provider" validate:"required" example:"twilio"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// SendResetCode godoc
|
// SendResetCode godoc
|
||||||
|
|
@ -242,7 +245,7 @@ func (h *Handler) SendResetCode(c *fiber.Ctx) error {
|
||||||
return fiber.NewError(fiber.StatusBadRequest, "Email or PhoneNumber must be provided")
|
return fiber.NewError(fiber.StatusBadRequest, "Email or PhoneNumber must be provided")
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := h.userSvc.SendResetCode(c.Context(), medium, sentTo); err != nil {
|
if err := h.userSvc.SendResetCode(c.Context(), medium, sentTo, req.Provider); err != nil {
|
||||||
h.logger.Error("Failed to send reset code", "error", err)
|
h.logger.Error("Failed to send reset code", "error", err)
|
||||||
fmt.Println(err)
|
fmt.Println(err)
|
||||||
return fiber.NewError(fiber.StatusInternalServerError, "Failed to send reset code")
|
return fiber.NewError(fiber.StatusInternalServerError, "Failed to send reset code")
|
||||||
|
|
|
||||||
|
|
@ -52,7 +52,7 @@ func (a *App) initAppRoutes() {
|
||||||
a.fiber.Get("/", func(c *fiber.Ctx) error {
|
a.fiber.Get("/", func(c *fiber.Ctx) error {
|
||||||
return c.JSON(fiber.Map{
|
return c.JSON(fiber.Map{
|
||||||
"message": "Welcome to the FortuneBet API",
|
"message": "Welcome to the FortuneBet API",
|
||||||
"version": "1.0dev3",
|
"version": "1.0dev6",
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
@ -146,6 +146,8 @@ func (a *App) initAppRoutes() {
|
||||||
a.fiber.Get("/branch/:id", a.authMiddleware, h.GetBranchByID)
|
a.fiber.Get("/branch/:id", a.authMiddleware, h.GetBranchByID)
|
||||||
a.fiber.Get("/branch/:id/bets", a.authMiddleware, h.GetBetByBranchID)
|
a.fiber.Get("/branch/:id/bets", a.authMiddleware, h.GetBetByBranchID)
|
||||||
a.fiber.Put("/branch/:id", a.authMiddleware, h.UpdateBranch)
|
a.fiber.Put("/branch/:id", a.authMiddleware, h.UpdateBranch)
|
||||||
|
a.fiber.Put("/branch/:id/set-active", a.authMiddleware, h.UpdateBranchStatus)
|
||||||
|
a.fiber.Put("/branch/:id/set-inactive", a.authMiddleware, h.UpdateBranchStatus)
|
||||||
a.fiber.Delete("/branch/:id", a.authMiddleware, h.DeleteBranch)
|
a.fiber.Delete("/branch/:id", a.authMiddleware, h.DeleteBranch)
|
||||||
a.fiber.Get("/search/branch", a.authMiddleware, h.SearchBranch)
|
a.fiber.Get("/search/branch", a.authMiddleware, h.SearchBranch)
|
||||||
// /branch/search
|
// /branch/search
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user