hackathon/db/quest.go

120 lines
2.8 KiB
Go

package db
import (
"context"
"database/sql"
"errors"
"fmt"
"github.com/hhhapz/codequest/models"
"github.com/hhhapz/codequest/question"
)
func (db *DB) Questions(ctx context.Context, u *models.User) ([]*question.Data, error) {
ui, err := models.UserInfoByUserID(ctx, db.DB, u.ID)
if errors.Is(err, sql.ErrNoRows) {
return nil, models.NewUserError("you must fill in your user details first")
}
if err != nil {
return nil, err
}
var questions []*question.Question
for _, q := range question.Questions {
if ui.SkillLevel != int(q.Level) {
continue
}
questions = append(questions, q)
}
parts, err := models.AllQuestionPartsData(ctx, db.DB, u.ID)
if err != nil {
return nil, err
}
var data []*question.Data
for _, q := range questions {
var p1, p2 question.PartData
for _, p := range parts {
if p.QuestionID == q.ID {
p1, p2 = question.PartData{
Completed: p.P1Awarded.Valid,
PointsWorth: int(p.P1Awarded.Int64),
}, question.PartData{
Completed: p.P2Awarded.Valid,
PointsWorth: int(p.P2Awarded.Int64),
}
}
break
}
data = append(data, &question.Data{
QuestionID: q.ID,
UserID: u.ID,
Name: q.Name,
Part1: p1,
Part2: p2,
})
}
return data, nil
}
func (db *DB) Question(ctx context.Context, u *models.User, id string) (*question.Data, error) {
ui, err := models.UserInfoByUserID(ctx, db.DB, u.ID)
if errors.Is(err, sql.ErrNoRows) {
return nil, models.NewUserError("you must fill in your user details first")
}
if err != nil {
return nil, err
}
var q *question.Question
for _, qq := range question.Questions {
if qq.ID != id {
continue
}
if ui.SkillLevel != int(qq.Level) {
return nil, models.NewUserError("this question is not available for your skill level")
}
q = qq
break
}
if q == nil {
return nil, models.NewUserError("question with the id %q not found", id)
}
partData, err := models.QuestionPartsData(ctx, db.DB, q.ID, u.ID)
if err != nil {
return nil, fmt.Errorf("could not retrieve question data: %w", err)
}
return &question.Data{
QuestionID: q.ID,
UserID: u.ID,
Name: q.Name,
Text: q.Text,
Level: q.Level,
Part1: question.PartData{
Completed: partData.P1Awarded.Valid,
PointsWorth: int(partData.P1Awarded.Int64),
},
Part2: question.PartData{
Completed: partData.P2Awarded.Valid,
PointsWorth: int(partData.P2Awarded.Int64),
},
}, nil
}
func (db *DB) Submissions(ctx context.Context, u *models.User, questionID string, part question.Part) (bool, int, error) {
s, err := models.QuestionSubmissions(ctx, db.DB, u.ID, questionID, int(part))
if err != nil {
return false, 0, err
}
return s.Correct, s.ByUser, nil
}
func (db *DB) AddSubmission(ctx context.Context, submission *models.QuestionAttempt) error {
return submission.Insert(ctx, db.DB)
}