package fic import ( "fmt" ) // FlagLabel represents a flag's challenge, stored as hash. type FlagLabel struct { Id int `json:"id"` // IdExercice is the identifier of the underlying challenge IdExercice int64 `json:"idExercice"` // Order is used to sort the flag between them Order int8 `json:"order"` // Label is the title of the flag as displayed to players Label string `json:"label"` // Variant stores the label color. Variant string `json:"variant"` } // GetFlagLabels returns a list of key's flags comming with the challenge. func (e *Exercice) GetFlagLabels() ([]*FlagLabel, error) { if rows, err := DBQuery("SELECT id_label, id_exercice, ordre, label, variant FROM exercice_flag_labels WHERE id_exercice = ?", e.Id); err != nil { return nil, err } else { defer rows.Close() flags := []*FlagLabel{} for rows.Next() { k := &FlagLabel{} k.IdExercice = e.Id if err := rows.Scan(&k.Id, &k.IdExercice, &k.Order, &k.Label, &k.Variant); err != nil { return nil, err } flags = append(flags, k) } if err := rows.Err(); err != nil { return nil, err } return flags, nil } } // GetFlagLabel returns a list of flags comming with the challenge. func GetFlagLabel(id int) (k *FlagLabel, err error) { k = &FlagLabel{} err = DBQueryRow("SELECT id_label, id_exercice, ordre, label, variant FROM exercice_flag_labels WHERE id_flag = ?", id).Scan(&k.Id, &k.IdExercice, &k.Order, &k.Label, &k.Variant) return } // GetFlagLabelByLabel returns a flag matching the given label. func (e *Exercice) GetFlagLabelByLabel(label string) (k *FlagLabel, err error) { k = &FlagLabel{} err = DBQueryRow("SELECT id_label, id_exercice, ordre, label, variant FROM exercice_flags WHERE type LIKE ? AND id_exercice = ?", label, e.Id).Scan(&k.Id, &k.IdExercice, &k.Order, &k.Label, &k.Variant) return } // GetId returns the Flag identifier. func (k *FlagLabel) GetId() int { return k.Id } // RecoverId returns the Flag identifier as register in DB. func (k *FlagLabel) RecoverId() (Flag, error) { if err := DBQueryRow("SELECT id_label FROM exercice_flag_labels WHERE label LIKE ? AND id_exercice = ?", k.Label, k.IdExercice).Scan(&k.Id); err != nil { return nil, err } else { return k, err } } // AddFlagLabel creates and fills a new struct Flag and registers it into the database. func (k *FlagLabel) Create(e *Exercice) (Flag, error) { if res, err := DBExec("INSERT INTO exercice_flag_labels (id_exercice, ordre, label, variant) VALUES (?, ?, ?, ?)", e.Id, k.Order, k.Label, k.Variant); err != nil { return k, err } else if kid, err := res.LastInsertId(); err != nil { return k, err } else { k.Id = int(kid) k.IdExercice = e.Id return k, nil } } // Update applies modifications back to the database. func (k *FlagLabel) Update() (int64, error) { if res, err := DBExec("UPDATE exercice_flag_labels SET id_exercice = ?, ordre = ?, label = ?, variant = ? WHERE id_label = ?", k.IdExercice, k.Order, k.Label, k.Variant, k.Id); err != nil { return 0, err } else if nb, err := res.RowsAffected(); err != nil { return 0, err } else { return nb, err } } // Delete the flag from the database. func (k *FlagLabel) Delete() (int64, error) { if _, err := DBExec("DELETE FROM exercice_flag_labels_deps WHERE id_label = ?", k.Id); err != nil { return 0, err } else if _, err := DBExec("DELETE FROM exercice_flag_labels_omcq_deps WHERE id_label = ?", k.Id); err != nil { return 0, err } else if res, err := DBExec("DELETE FROM exercice_flag_labels WHERE id_label = ?", k.Id); err != nil { return 0, err } else if nb, err := res.RowsAffected(); err != nil { return 0, err } else { return nb, err } } func (k *FlagLabel) GetOrder() int8 { return k.Order } // AddDepend insert a new dependency to a given flag. func (k *FlagLabel) AddDepend(j Flag) (err error) { if d, ok := j.(*FlagKey); ok { _, err = DBExec("INSERT INTO exercice_flag_labels_deps (id_label, id_flag_dep) VALUES (?, ?)", k.Id, d.Id) } else if d, ok := j.(*MCQ); ok { _, err = DBExec("INSERT INTO exercice_flag_labels_omcq_deps (id_label, id_mcq_dep) VALUES (?, ?)", k.Id, d.Id) } else { err = fmt.Errorf("dependancy type for key (%T) not implemented for this flag", j) } return } // GetDepends retrieve the flag's dependency list. func (k *FlagLabel) GetDepends() ([]Flag, error) { var deps []Flag if rows, err := DBQuery("SELECT id_flag_dep FROM exercice_flag_labels_deps WHERE id_label = ?", k.Id); err != nil { return nil, err } else { defer rows.Close() for rows.Next() { var d int if err := rows.Scan(&d); err != nil { return nil, err } deps = append(deps, &FlagKey{Id: d, IdExercice: k.IdExercice}) } if err := rows.Err(); err != nil { return nil, err } } if rows, err := DBQuery("SELECT id_mcq_dep FROM exercice_flag_labels_omcq_deps WHERE id_label = ?", k.Id); err != nil { return nil, err } else { defer rows.Close() for rows.Next() { var d int if err := rows.Scan(&d); err != nil { return nil, err } deps = append(deps, &MCQ{Id: d, IdExercice: k.IdExercice}) } if err := rows.Err(); err != nil { return nil, err } } return deps, nil } // Check if the given val is the expected one for this flag. func (k *FlagLabel) Check(v interface{}) int { return 0 } // FoundBy registers in the database that the given Team solved the flag. func (k *FlagLabel) FoundBy(t *Team) { } // GetExercice returns the parent Exercice where this flag can be found. func (k *FlagLabel) GetExercice() (*Exercice, error) { var eid int64 if err := DBQueryRow("SELECT id_exercice FROM exercice_flag_labels WHERE id_label = ?", k.Id).Scan(&eid); err != nil { return nil, err } return GetExercice(eid) }