# Complete Example

## Program

The previous examples in the logr documentation were intentionally simplified to focus on the workings of a particular function. It is helpful, however, to also view logr functions in the context of a complete program. The following example shows a complete program. The example illustrates how logr functions work together, and interact with tidyverse and sassy functions to create a comprehensive log.

This example has been chosen because it incorporates many of the functions that will log automatically. If you want to maximize the auto-generation features of logr, take note of these functions.

The data for this example has been included in the logr package as an external data file. It may be accessed using the `system.file()` function as shown below, or downloaded directly from the logr GitHub site here

    library(tidyverse)
    library(sassy)

    options("logr.autolog" = TRUE)

    # Get temp location for log and report output
    tmp <- tempdir()

    # Open the log
    lf <- log_open(file.path(tmp, "example1.log"))

    # Send code to the log
    log_code()

    sep("Load the data")

    # Get path to sample data
    pkg <- system.file("extdata", package = "logr")

    # Define data library
    libname(sdtm, pkg, "csv")

    # Prepare Data -------------------------------------------------------------
    sep("Prepare the data")

    # Define format for age groups
    ageg <- value(condition(x > 18 & x <= 29, "18 to 29"),
                  condition(x >= 30 & x <= 44, "30 to 44"),
                  condition(x >= 45 & x <= 59, "45 to 59"),
                  condition(TRUE, "60+"))

    # Manipulate data
    final <- sdtm$DM %>%
      select(USUBJID, BRTHDTC, AGE) %>%
      mutate(AGEG = fapply(AGE, ageg)) %>%
      arrange(AGEG, AGE) %>%
      group_by(AGEG) %>%
      datastep(retain = list(SEQ = 0),
               calculate = {AGEM <- mean(AGE)},
               attrib = list(USUBJID = dsattr(label = "Universal Subject ID"),
                             BRTHDTC = dsattr(label = "Subject Birth Date",
                                              format = "%m %B %Y"),
                             AGE = dsattr(label = "Subject Age in Years",
                                          justify = "center"),
                             AGEG = dsattr(label = "Subject Age Group",
                                           justify = "left"),
                             AGEB = dsattr(label = "Age Group Boundaries"),
                             SEQ = dsattr(label = "Subject Age Group Sequence",
                                          justify = "center"),
                             AGEM = dsattr(label = "Mean Subject Age",
                                           format = "%1.2f"),
                             AGEMC = dsattr(label = "Subject Age Mean Category",
                                            format = c(B = "Below", A = "Above"),
                                            justify = "right")),
               {

                 # Start and end of Age Groups
                 if (first. & last.)
                   AGEB <- "Start - End"
                 else if (first.)
                   AGEB <- "Start"
                 else if (last.)
                   AGEB <- "End"
                 else
                   AGEB <- "-"

                 # Sequence within Age Groups
                 if (first.)
                   SEQ <- 1
                 else
                   SEQ <- SEQ + 1

                 # Above or Below the mean age
                 if (AGE > AGEM)
                   AGEMC <- "A"
                 else
                   AGEMC <- "B"

               }) %>%
      ungroup() %>%
      put()

    # Put dictionary to log
    dictionary(final) %>% put()

    # Create Report ------------------------------------------------------------
    sep("Create report")

    # Create table
    tbl <- create_table(final)

    # Create report
    rpt <- create_report(file.path(tmp, "./output/example1.rtf"),
                         output_type = "RTF", font = "Arial") %>%
      titles("Our first SASSY report", bold = TRUE) %>%
      add_content(tbl)

    # write out the report
    res <- write_report(rpt)

    # Clean Up -----------------------------------------------------------------
    sep("Clean Up")

    # Close the log
    log_close()

    # View Report
    # file.show(res$modified_path)

    # View Log
    # file.show(lf)

## Output

Here is the report produced by the sample program:

## Log

The above program produces the following log:

    =========================================================================
    Log Path: C:/Users/dbosa/AppData/Local/Temp/Rtmpw1TuO2/log/example1.log
    Program Path: C:/packages/Testing/LogTest24.R
    Working Directory: C:/packages/Testing
    User Name: dbosa
    R Version: 4.4.2 (2024-10-31 ucrt)
    Machine: SOCRATES x86-64
    Operating System: Windows 10 x64 build 26100
    Base Packages: stats graphics grDevices utils datasets methods base
    Other Packages: tidylog_1.1.0 procs_1.0.7 reporter_1.4.4 libr_1.3.4 logr_1.3.9
    fmtr_1.6.5 common_1.1.3 sassy_1.2.5 lubridate_1.9.3 forcats_1.0.0 stringr_1.5.1
    dplyr_1.1.4 purrr_1.0.2 readr_2.1.5 tidyr_1.3.1 tibble_3.2.1 ggplot2_3.5.1
    tidyverse_2.0.0
    Log Start Time: 2025-03-26 12:50:40.218714
    =========================================================================

    > library(tidyverse)
    > library(sassy)
    >
    > options("logr.autolog" = TRUE)
    >
    > # Get temp location for log and report output
    > tmp <- tempdir()
    >
    > # Open the log
    > lf <- log_open(file.path(tmp, "example1.log"))
    >
    > # Send code to the log
    > log_code()
    >
    > sep("Load the data")
    >
    > # Get path to sample data
    > pkg <- system.file("extdata", package = "logr")
    >
    > # Define data library
    > libname(sdtm, pkg, "csv")
    >
    > # Prepare Data -------------------------------------------------------------
    > sep("Prepare the data")
    >
    > # Define format for age groups
    > ageg <- value(condition(x > 18 & x <= 29, "18 to 29"),
    >               condition(x >= 30 & x <= 44, "30 to 44"),
    >               condition(x >= 45 & x <= 59, "45 to 59"),
    >               condition(TRUE, "60+"))
    >
    >
    > # Manipulate data
    > final <- sdtm$DM %>%
    >   select(USUBJID, BRTHDTC, AGE) %>%
    >   mutate(AGEG = fapply(AGE, ageg)) %>%
    >   arrange(AGEG, AGE) %>%
    >   group_by(AGEG) %>%
    >   datastep(retain = list(SEQ = 0),
    >            calculate = {AGEM <- mean(AGE)},
    >            attrib = list(USUBJID = dsattr(label = "Universal Subject ID"),
    >                          BRTHDTC = dsattr(label = "Subject Birth Date",
    >                                           format = "%m %B %Y"),
    >                          AGE = dsattr(label = "Subject Age in Years",
    >                                       justify = "center"),
    >                          AGEG = dsattr(label = "Subject Age Group",
    >                                        justify = "left"),
    >                          AGEB = dsattr(label = "Age Group Boundaries"),
    >                          SEQ = dsattr(label = "Subject Age Group Sequence",
    >                                       justify = "center"),
    >                          AGEM = dsattr(label = "Mean Subject Age",
    >                                        format = "%1.2f"),
    >                          AGEMC = dsattr(label = "Subject Age Mean Category",
    >                                         format = c(B = "Below", A = "Above"),
    >                                         justify = "right")),
    >            {
    >
    >              # Start and end of Age Groups
    >              if (first. & last.)
    >                AGEB <- "Start - End"
    >              else if (first.)
    >                AGEB <- "Start"
    >              else if (last.)
    >                AGEB <- "End"
    >              else
    >                AGEB <- "-"
    >
    >              # Sequence within Age Groups
    >              if (first.)
    >                SEQ <- 1
    >              else
    >                SEQ <- SEQ + 1
    >
    >              # Above or Below the mean age
    >              if (AGE > AGEM)
    >                AGEMC <- "A"
    >              else
    >                AGEMC <- "B"
    >
    >            }) %>%
    >   ungroup() %>%
    >   put()
    >
    > # Put dictionary to log
    > dictionary(final) %>% put()
    >
    > # Create Report ------------------------------------------------------------
    > sep("Create report")
    >
    >
    > # Create table
    > tbl <- create_table(final)
    >
    > # Create report
    > rpt <- create_report(file.path(tmp, "./output/example1.rtf"),
    >                      output_type = "RTF", font = "Arial") %>%
    >   titles("Our first SASSY report", bold = TRUE) %>%
    >   add_content(tbl)
    >
    > # write out the report
    > res <- write_report(rpt)
    >
    >
    > # Clean Up -----------------------------------------------------------------
    > sep("Clean Up")
    >
    > # Close the log
    > log_close()
    >
    > # View Report
    > # file.show(res$modified_path)
    >
    > # View Log
    > # file.show(lf)
    >
    >
    >

    =========================================================================
    Load the data
    =========================================================================

    # library 'sdtm': 1 items
    - attributes: csv not loaded
    - path: C:/Users/dbosa/AppData/Local/R/win-library/4.4/logr/extdata
    - items:
      Name Extension Rows Cols    Size        LastModified
    1   DM       csv   87   24 45.8 Kb 2025-03-26 11:02:29

    NOTE: Log Print Time:  2025-03-26 12:50:40.733955
    NOTE: Elapsed Time: 0.511612892150879 secs

    =========================================================================
    Prepare the data
    =========================================================================

    # A user-defined format: 4 conditions
      Name Type        Expression    Label Order
    1  obj    U  x > 18 & x <= 29 18 to 29    NA
    2  obj    U x >= 30 & x <= 44 30 to 44    NA
    3  obj    U x >= 45 & x <= 59 45 to 59    NA
    4  obj    U              TRUE      60+    NA

    NOTE: Log Print Time:  2025-03-26 12:50:40.74675
    NOTE: Elapsed Time: 0.0127952098846436 secs

    select: dropped 21 variables (STUDYID, DOMAIN, SUBJID, RFSTDTC, RFENDTC, …)

    NOTE: Log Print Time:  2025-03-26 12:50:40.759215
    NOTE: Elapsed Time: 0.0124650001525879 secs

    mutate: new variable 'AGEG' (character) with 4 unique values and 0% NA

    NOTE: Log Print Time:  2025-03-26 12:50:40.779213
    NOTE: Elapsed Time: 0.0199978351593018 secs

    group_by: one grouping variable (AGEG)

    NOTE: Log Print Time:  2025-03-26 12:50:40.79064
    NOTE: Elapsed Time: 0.0114271640777588 secs

    datastep: columns increased from 4 to 8

    NOTE: Log Print Time:  2025-03-26 12:50:40.911893
    NOTE: Elapsed Time: 0.121252775192261 secs

    # A tibble: 87 × 8
    # Groups:   AGEG [4]
       USUBJID    BRTHDTC      AGE AGEG      AGEM AGEB    SEQ AGEMC
       <chr>      <date>     <dbl> <chr>    <dbl> <chr> <dbl> <chr>
     1 ABC-04-128 1987-05-24    19 18 to 29  49.4 Start     1 B
     2 ABC-07-011 1985-01-18    21 18 to 29  49.4 -         2 B
     3 ABC-09-139 1985-11-13    21 18 to 29  49.4 -         3 B
     4 ABC-09-018 1984-08-29    22 18 to 29  49.4 -         4 B
     5 ABC-04-074 1983-03-28    23 18 to 29  49.4 -         5 B
     6 ABC-01-053 1980-04-07    26 18 to 29  49.4 -         6 B
     7 ABC-06-070 1980-02-01    26 18 to 29  49.4 End       7 B
     8 ABC-02-112 1976-11-01    30 30 to 44  49.4 Start     1 B
     9 ABC-01-056 1975-05-02    31 30 to 44  49.4 -         2 B
    10 ABC-03-089 1975-10-02    31 30 to 44  49.4 -         3 B
    # ℹ 77 more rows
    # ℹ Use `print(n = ...)` to see more rows

    NOTE: Data frame has 87 rows and 8 columns.

    NOTE: Log Print Time:  2025-03-26 12:50:40.993307
    NOTE: Elapsed Time: 0.0814142227172852 secs

    ungroup: no grouping variables remain

    NOTE: Log Print Time:  2025-03-26 12:50:41.067702
    NOTE: Elapsed Time: 0.0743949413299561 secs

    # A tibble: 87 × 8
       USUBJID    BRTHDTC      AGE AGEG      AGEM AGEB    SEQ AGEMC
       <chr>      <date>     <dbl> <chr>    <dbl> <chr> <dbl> <chr>
     1 ABC-04-128 1987-05-24    19 18 to 29  49.4 Start     1 B
     2 ABC-07-011 1985-01-18    21 18 to 29  49.4 -         2 B
     3 ABC-09-139 1985-11-13    21 18 to 29  49.4 -         3 B
     4 ABC-09-018 1984-08-29    22 18 to 29  49.4 -         4 B
     5 ABC-04-074 1983-03-28    23 18 to 29  49.4 -         5 B
     6 ABC-01-053 1980-04-07    26 18 to 29  49.4 -         6 B
     7 ABC-06-070 1980-02-01    26 18 to 29  49.4 End       7 B
     8 ABC-02-112 1976-11-01    30 30 to 44  49.4 Start     1 B
     9 ABC-01-056 1975-05-02    31 30 to 44  49.4 -         2 B
    10 ABC-03-089 1975-10-02    31 30 to 44  49.4 -         3 B
    # ℹ 77 more rows
    # ℹ Use `print(n = ...)` to see more rows

    NOTE: Data frame has 87 rows and 8 columns.

    NOTE: Log Print Time:  2025-03-26 12:50:41.219635
    NOTE: Elapsed Time: 0.151932954788208 secs

    # A tibble: 8 × 11
      Name  Column  Class    Label Description Format Width Justify  Rows   NAs MaxChar
      <chr> <chr>   <chr>    <chr> <chr>       <chr>  <lgl> <chr>   <int> <int>   <int>
    1 final USUBJID charact… Univ… <NA>         <NA>  NA    <NA>       87     0      10
    2 final BRTHDTC Date     Subj… <NA>        "%m %… NA    <NA>       87     0      10
    3 final AGE     numeric  Subj… <NA>         <NA>  NA    center     87     0       2
    4 final AGEG    charact… Subj… <NA>         <NA>  NA    left       87     0       8
    5 final AGEM    numeric  Mean… <NA>        "%1.2… NA    <NA>       87     0      16
    6 final AGEB    charact… Age … <NA>         <NA>  NA    <NA>       87     0       5
    7 final SEQ     numeric  Subj… <NA>         <NA>  NA    center     87     0       2
    8 final AGEMC   charact… Subj… <NA>        "Belo… NA    right      87     0       1

    NOTE: Data frame has 8 rows and 11 columns.

    NOTE: Log Print Time:  2025-03-26 12:50:41.40138
    NOTE: Elapsed Time: 0.181745052337646 secs

    =========================================================================
    Create report
    =========================================================================

    # A report specification: 3 pages
    - file_path: 'C:\Users\dbosa\AppData\Local\Temp\Rtmpw1TuO2/./output/example1.rtf'
    - output_type: RTF
    - units: inches
    - orientation: landscape
    - margins: top 0.5 bottom 0.5 left 1 right 1
    - line size/count: 9/42
    - title 1: 'Our first SASSY report'
    - content:
    # A table specification:
    - data: tibble 'final' 87 rows 8 cols
    - show_cols: all
    - use_attributes: all

    NOTE: Log Print Time:  2025-03-26 12:50:41.999186
    NOTE: Elapsed Time: 0.597805976867676 secs

    =========================================================================
    Clean Up
    =========================================================================

    =========================================================================
    Log End Time: 2025-03-26 12:50:42.151877
    Log Elapsed Time: 0 00:00:01
    =========================================================================