Skip to contents

This vignette shows a minimal teacher workflow: declare course metadata, tutorial metadata, students, and expected questions; record attempts; inspect group-level results; and export CSV files.

Create a configuration directory

library(learnrTrackR)

config_dir <- tempfile()
dir.create(config_dir)

readr::write_csv(
  data.frame(
    course_id = "stat101",
    course_label = "Statistics 101",
    semester = "W2026"
  ),
  file.path(config_dir, "courses.csv")
)

readr::write_csv(
  data.frame(
    tutorial_id = "module_01",
    course_id = "stat101",
    tutorial_label = "Module 1",
    version = "0.0.1"
  ),
  file.path(config_dir, "tutorials.csv")
)

readr::write_csv(
  data.frame(
    student_id = c("student_001", "student_002", "student_003"),
    student_label = c("Student 1", "Student 2", "Student 3"),
    group_id = c("A", "A", "B")
  ),
  file.path(config_dir, "students.csv")
)

readr::write_csv(
  data.frame(
    tutorial_id = "module_01",
    question_id = c("q1", "q2"),
    question_label = c("Mean exercise", "Summary exercise"),
    question_type = c("code", "code"),
    max_score = c(1, 1)
  ),
  file.path(config_dir, "questions.csv")
)

The same fields can also be represented in a YAML file and read with read_tracking_config() when the yaml package is installed.

Load the configuration

db_path <- tempfile(fileext = ".sqlite")
con <- init_tracking_db(db_path, overwrite = TRUE)

load_tracking_config(con, config_dir)
#> $courses
#> # A tibble: 1 × 4
#>   course_id course_label   semester created_at          
#>   <chr>     <chr>          <chr>    <chr>               
#> 1 stat101   Statistics 101 W2026    2026-06-24T12:25:43Z
#> 
#> $tutorials
#> # A tibble: 1 × 5
#>   tutorial_id course_id tutorial_label version created_at          
#>   <chr>       <chr>     <chr>          <chr>   <chr>               
#> 1 module_01   stat101   Module 1       0.0.1   2026-06-24T12:25:43Z
#> 
#> $students
#> # A tibble: 3 × 5
#>   student_id  student_label email group_id created_at          
#>   <chr>       <chr>         <chr> <chr>    <chr>               
#> 1 student_001 Student 1     NA    A        2026-06-24T12:25:43Z
#> 2 student_002 Student 2     NA    A        2026-06-24T12:25:43Z
#> 3 student_003 Student 3     NA    B        2026-06-24T12:25:43Z
#> 
#> $questions
#> # A tibble: 2 × 6
#>   question_id tutorial_id question_label   question_type max_score created_at   
#>   <chr>       <chr>       <chr>            <chr>             <dbl> <chr>        
#> 1 q1          module_01   Mean exercise    code                  1 2026-06-24T1…
#> 2 q2          module_01   Summary exercise code                  1 2026-06-24T1…

Record attempts

track_attempt(
  con,
  student_id = "student_001",
  tutorial_id = "module_01",
  question_id = "q1",
  submitted_answer = "mean(x)",
  grade_status = "correct",
  score = 1,
  max_score = 1,
  require_registered_student = TRUE
)

track_attempt(
  con,
  student_id = "student_002",
  tutorial_id = "module_01",
  question_id = "q1",
  submitted_answer = "sd(x)",
  grade_status = "incorrect",
  score = 0,
  max_score = 1,
  require_registered_student = TRUE
)

Inspect group results

group_a <- dashboard_data(
  con,
  tutorial_id = "module_01",
  group_id = "A",
  rule = "last"
)

group_a$summary
#> # A tibble: 9 × 2
#>   metric              value    
#>   <chr>               <chr>    
#> 1 Tutorial            module_01
#> 2 Group               A        
#> 3 Students            2        
#> 4 Attempts            2        
#> 5 Questions           2        
#> 6 Completed           0        
#> 7 Completion rate (%) 0.0      
#> 8 Mean percent        25.0     
#> 9 Median percent      25.0
group_a$students
#> # A tibble: 2 × 6
#>   student_id  student_label email group_id n_attempts has_attempts
#>   <chr>       <chr>         <chr> <chr>         <int> <lgl>       
#> 1 student_001 Student 1     NA    A                 1 TRUE        
#> 2 student_002 Student 2     NA    A                 1 TRUE
group_a$gradebook
#> # A tibble: 2 × 12
#>   student_id  student_label email group_id tutorial_id score max_score percent
#>   <chr>       <chr>         <chr> <chr>    <chr>       <dbl>     <dbl>   <dbl>
#> 1 student_001 Student 1     NA    A        module_01       1         2      50
#> 2 student_002 Student 2     NA    A        module_01       0         2       0
#> # ℹ 4 more variables: n_questions <int>, n_answered <int>, n_unanswered <int>,
#> #   completed <lgl>

Export teaching files

export_dir <- tempfile()
exported <- export_tracking_bundle(
  con,
  export_dir,
  tutorial_id = "module_01",
  group_id = "A",
  rule = "last"
)

exported
#> # A tibble: 8 × 2
#>   table         path                                                            
#>   <chr>         <chr>                                                           
#> 1 summary       /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-summary.csv   
#> 2 students      /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-students.csv  
#> 3 attempts      /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-attempts.csv  
#> 4 scores        /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-scores.csv    
#> 5 gradebook     /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-gradebook.csv 
#> 6 questions     /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-questions.csv 
#> 7 moodle_grades /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-moodle_grades…
#> 8 canvas_grades /tmp/RtmprrTSa4/file1fe686e4791/module_01-group-A-canvas_grades…
file.exists(exported$path)
#> [1] TRUE TRUE TRUE TRUE TRUE TRUE TRUE TRUE

The bundle contains summary, students, attempts, scores, gradebook, questions, and Moodle-ready grade CSV files.