From 5d31ac6e04d6eb704157c201e7a5853217fba499 Mon Sep 17 00:00:00 2001 From: Pierre-Olivier Mercier Date: Wed, 16 Jan 2019 06:02:06 +0100 Subject: [PATCH] libfic: implement more dependancies kind --- libfic/db.go | 20 ++++++++++++++++++++ libfic/flag.go | 6 +++++- libfic/flag_key.go | 35 ++++++++++++++++++++++++++++++----- libfic/mcq.go | 37 ++++++++++++++++++++++++++++++++++--- libfic/team_my.go | 5 +++++ 5 files changed, 94 insertions(+), 9 deletions(-) diff --git a/libfic/db.go b/libfic/db.go index d61f1536..9f3bcec0 100644 --- a/libfic/db.go +++ b/libfic/db.go @@ -216,6 +216,26 @@ CREATE TABLE IF NOT EXISTS exercice_mcq( title VARCHAR(255) NOT NULL, FOREIGN KEY(id_exercice) REFERENCES exercices(id_exercice) ) DEFAULT CHARACTER SET = utf8mb4 COLLATE = utf8mb4_unicode_ci; +`); err != nil { + return err + } + if _, err := db.Exec(` +CREATE TABLE IF NOT EXISTS exercice_mcq_okey_deps( + id_mcq INTEGER NOT NULL, + id_flag_dep INTEGER NOT NULL, + FOREIGN KEY(id_mcq) REFERENCES exercice_mcq(id_mcq), + FOREIGN KEY(id_flag_dep) REFERENCES exercice_flags(id_flag) +) DEFAULT CHARACTER SET = utf8 COLLATE = utf8_bin; +`); err != nil { + return err + } + if _, err := db.Exec(` +CREATE TABLE IF NOT EXISTS exercice_flags_omcq_deps( + id_flag INTEGER NOT NULL, + id_mcq_dep INTEGER NOT NULL, + FOREIGN KEY(id_flag) REFERENCES exercice_flags(id_flag), + FOREIGN KEY(id_mcq_dep) REFERENCES exercice_mcq(id_mcq) +) DEFAULT CHARACTER SET = utf8 COLLATE = utf8_bin; `); err != nil { return err } diff --git a/libfic/flag.go b/libfic/flag.go index 14a675c2..9f9eee7b 100644 --- a/libfic/flag.go +++ b/libfic/flag.go @@ -38,7 +38,11 @@ func (e Exercice) GetFlags() ([]Flag, error) { func (e Exercice) WipeFlags() (int64, error) { if _, err := DBExec("DELETE FROM exercice_files_deps WHERE id_flag IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id); err != nil { return 0, err - } else if _, err := DBExec("DELETE FROM exercice_flags_deps WHERE id_flag IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id); err != nil { + } else if _, err := DBExec("DELETE FROM exercice_flags_deps WHERE id_flag IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?) OR id_flag_dep IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id, e.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_flags_omcq_deps WHERE id_flag IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_mcq_okey_deps WHERE id_flag_dep IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id); err != nil { return 0, err } else if _, err := DBExec("DELETE FROM team_wchoices WHERE id_flag IN (SELECT id_flag FROM exercice_flags WHERE id_exercice = ?)", e.Id); err != nil { return 0, err diff --git a/libfic/flag_key.go b/libfic/flag_key.go index 0324325b..01708a12 100644 --- a/libfic/flag_key.go +++ b/libfic/flag_key.go @@ -3,6 +3,7 @@ package fic import ( "bytes" "errors" + "fmt" "regexp" "time" @@ -139,7 +140,11 @@ func (k FlagKey) Update() (int64, error) { func (k FlagKey) Delete() (int64, error) { if _, err := DBExec("DELETE FROM exercice_files_deps WHERE id_flag = ?", k.Id); err != nil { return 0, err - } else if _, err := DBExec("DELETE FROM exercice_flags_deps WHERE id_flag = ?", k.Id); err != nil { + } else if _, err := DBExec("DELETE FROM exercice_mcq_okey_deps WHERE id_flag_dep = ?", k.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_flags_omcq_deps WHERE id_flag = ?", k.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_flags_deps WHERE id_flag = ? OR id_flag_dep = ?", k.Id, k.Id); err != nil { return 0, err } else if _, err := DBExec("DELETE FROM flag_choices WHERE id_flag = ?", k.Id); err != nil { return 0, err @@ -156,20 +161,23 @@ func (k FlagKey) Delete() (int64, error) { func (k FlagKey) AddDepend(j Flag) (err error) { if d, ok := j.(FlagKey); ok { _, err = DBExec("INSERT INTO exercice_flags_deps (id_flag, id_flag_dep) VALUES (?, ?)", k.Id, d.Id) + } else if d, ok := j.(MCQ); ok { + _, err = DBExec("INSERT INTO exercice_flags_omcq_deps (id_flag, id_mcq_dep) VALUES (?, ?)", k.Id, d.Id) } else { - err = errors.New("Dependancy type not implemented for this flag.") + err = errors.New(fmt.Sprintf("Dependancy type for key (%T) not implemented for this flag.", j)) } return } // GetDepends retrieve the flag's dependency list. func (k FlagKey) GetDepends() ([]Flag, error) { + var deps = make([]Flag, 0) + if rows, err := DBQuery("SELECT id_flag_dep FROM exercice_flags_deps WHERE id_flag = ?", k.Id); err != nil { return nil, err } else { defer rows.Close() - var deps = make([]Flag, 0) for rows.Next() { var d int64 if err := rows.Scan(&d); err != nil { @@ -180,9 +188,26 @@ func (k FlagKey) GetDepends() ([]Flag, error) { if err := rows.Err(); err != nil { return nil, err } - - return deps, nil } + + if rows, err := DBQuery("SELECT id_mcq_dep FROM exercice_flags_omcq_deps WHERE id_flag = ?", k.Id); err != nil { + return nil, err + } else { + defer rows.Close() + + for rows.Next() { + var d int64 + if err := rows.Scan(&d); err != nil { + return nil, err + } + deps = append(deps, MCQ{d, k.IdExercice, "", []MCQ_entry{}}) + } + if err := rows.Err(); err != nil { + return nil, err + } + } + + return deps, nil } // Check if the given val is the expected one for this flag. diff --git a/libfic/mcq.go b/libfic/mcq.go index 4f1968cc..50f8539b 100644 --- a/libfic/mcq.go +++ b/libfic/mcq.go @@ -121,7 +121,11 @@ func (m MCQ) Update() (int64, error) { // Delete the MCQ from the database. func (m MCQ) Delete() (int64, error) { - if res, err := DBExec("DELETE FROM exercice_mcq WHERE id_mcq = ?", m.Id); err != nil { + if _, err := DBExec("DELETE FROM exercice_mcq_okey_deps WHERE id_mcq = ?", m.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_flags_omcq_deps WHERE id_mcq_dep = ?", m.Id); err != nil { + return 0, err + } else if res, err := DBExec("DELETE FROM exercice_mcq WHERE id_mcq = ?", m.Id); err != nil { return 0, err } else if nb, err := res.RowsAffected(); err != nil { return 0, err @@ -167,6 +171,10 @@ func (n MCQ_entry) Delete() (int64, error) { func (e Exercice) WipeMCQs() (int64, error) { if _, err := DBExec("DELETE FROM mcq_entries WHERE id_mcq IN (SELECT id_mcq FROM exercice_mcq WHERE id_exercice = ?);", e.Id); err != nil { return 0, err + } else if _, err := DBExec("DELETE FROM exercice_flags_omcq_deps WHERE id_mcq_dep IN (SELECT id_mcq FROM exercice_mcq WHERE id_exercice = ?);", e.Id); err != nil { + return 0, err + } else if _, err := DBExec("DELETE FROM exercice_mcq_okey_deps WHERE id_mcq IN (SELECT id_mcq FROM exercice_mcq WHERE id_exercice = ?);", e.Id); err != nil { + return 0, err } else if res, err := DBExec("DELETE FROM exercice_mcq WHERE id_exercice = ?;", e.Id); err != nil { return 0, err } else if nb, err := res.RowsAffected(); err != nil { @@ -178,12 +186,35 @@ func (e Exercice) WipeMCQs() (int64, error) { // AddDepend insert a new dependency to a given flag. func (m MCQ) AddDepend(j Flag) (err error) { - return errors.New("Dependancy type not implemented for this flag.") + if d, ok := j.(FlagKey); ok { + _, err = DBExec("INSERT INTO exercice_mcq_okey_deps (id_mcq, id_flag_dep) VALUES (?, ?)", m.Id, d.Id) + } else { + err = errors.New("Dependancy type not implemented for this flag.") + } + return } // GetDepends retrieve the flag's dependency list. func (m MCQ) GetDepends() ([]Flag, error) { - return nil, errors.New("Dependancy not implemented for MCQs.") + if rows, err := DBQuery("SELECT id_flag_dep FROM exercice_mcq_okey_deps WHERE id_mcq = ?", m.Id); err != nil { + return nil, err + } else { + defer rows.Close() + + var deps = make([]Flag, 0) + for rows.Next() { + var d int64 + if err := rows.Scan(&d); err != nil { + return nil, err + } + deps = append(deps, MCQ{d, m.IdExercice, "", []MCQ_entry{}}) + } + if err := rows.Err(); err != nil { + return nil, err + } + + return deps, nil + } } // GetJustifiedFlag searchs for a flag in the scope of the given exercice. diff --git a/libfic/team_my.go b/libfic/team_my.go index acb2a7be..9cf71ae6 100644 --- a/libfic/team_my.go +++ b/libfic/team_my.go @@ -232,6 +232,11 @@ func MyJSONTeam(t *Team, started bool) (interface{}, error) { return nil, err } else { for _, mcq := range mcqs { + if t != nil && !t.CanSeeFlag(mcq) { + // Dependancy missing, skip the flag for now + continue + } + m := myTeamMCQ{ Title: mcq.Title, Choices: map[int64]interface{}{},