Files
qv/internal/models/votes.go

108 lines
2.1 KiB
Go

package models
import (
"database/sql"
"errors"
"time"
)
type VoteModelInterface interface {
Insert(voterIdentity string, electionId string, choiceText string, tokens int) (int, error)
Exists(voterIdentity string, electionID string) (bool, error)
GetByElection(electionID string) (*[]Vote, error)
}
type VoteModel struct {
DB *sql.DB
}
type Vote struct {
VoterIdentity string
ElectionID string
ChoiceText string
Tokens int
CreatedAt time.Time
}
func (v *VoteModel) Insert(voterIdentity string, electionId string, choiceText string, tokens int) (int, error) {
tx, err := v.DB.Begin()
if err != nil {
return 0, err
}
defer tx.Rollback()
result, err := tx.Exec(`
INSERT INTO votes (voter_identity, election_id, choice_text, tokens)
VALUES (?, ?, ?, ?)`,
voterIdentity, electionId, choiceText, tokens)
if err != nil {
return 0, err
}
if err = tx.Commit(); err != nil {
return 0, err
}
voteId, err := result.LastInsertId()
return int(voteId), nil
}
func (v *VoteModel) Exists(voterIdentity string, electionID string) (bool, error) {
var exists bool
query := `
SELECT EXISTS (
SELECT 1
FROM votes
WHERE voter_identity = ? AND election_id = ?
)
`
err := v.DB.QueryRow(query, voterIdentity, electionID).Scan(&exists)
if err != nil {
if errors.Is(sql.ErrNoRows, err) {
return false, nil
}
return false, err
}
return exists, nil
}
func (v *VoteModel) GetByElection(electionID string) (*[]Vote, error) {
query := `
SELECT voter_identity, election_id, choice_text, tokens, created_at
FROM votes
WHERE election_id = ?
`
rows, err := v.DB.Query(query, electionID)
if err != nil {
return nil, err
}
defer rows.Close()
var votes []Vote
for rows.Next() {
var vote Vote
err := rows.Scan(
&vote.VoterIdentity,
&vote.ElectionID,
&vote.ChoiceText,
&vote.Tokens,
&vote.CreatedAt,
)
if err != nil {
return nil, err
}
votes = append(votes, vote)
}
if err = rows.Err(); err != nil {
return nil, err
}
if len(votes) == 0 {
return nil, sql.ErrNoRows
}
return &votes, nil
}