├── .Rbuildignore ├── .github └── workflows │ └── basic_checks.yaml ├── .gitignore ├── DESCRIPTION ├── Dockerfile ├── NAMESPACE ├── README.md ├── _pkgdown.yml └── vignettes └── CreateAPackage.Rmd /.Rbuildignore: -------------------------------------------------------------------------------- 1 | ^LICENSE\.md$ 2 | .github 3 | Dockerfile 4 | _pkgdown.yml 5 | -------------------------------------------------------------------------------- /.github/workflows/basic_checks.yaml: -------------------------------------------------------------------------------- 1 | on: [push] 2 | jobs: 3 | job1: 4 | runs-on: ubuntu-latest 5 | container: bioconductor/bioconductor_docker:devel 6 | steps: 7 | - uses: actions/checkout@v1 8 | 9 | - name: Query dependencies 10 | run: | 11 | install.packages('remotes') 12 | saveRDS(remotes::dev_package_deps(dependencies = TRUE), ".github/depends.Rds", version = 2) 13 | shell: Rscript {0} 14 | 15 | - name: Cache R packages 16 | if: runner.os != 'Windows' 17 | uses: actions/cache@v1 18 | with: 19 | path: /usr/local/lib/R/site-library 20 | key: ${{ runner.os }}-r-1-${{ hashFiles('.github/depends.Rds') }} 21 | restore-keys: ${{ runner.os }}-r-1- 22 | 23 | - name: Install dependencies 24 | run: | 25 | remotes::install_deps(dependencies = TRUE, repos = BiocManager::repositories()) 26 | remotes::install_cran("rcmdcheck") 27 | shell: Rscript {0} 28 | 29 | - name: Check 30 | env: 31 | _R_CHECK_CRAN_INCOMING_REMOTE_: false 32 | run: rcmdcheck::rcmdcheck(args = c("--no-manual"), error_on = "warning", check_dir = "check") 33 | shell: Rscript {0} 34 | 35 | - uses: docker/build-push-action@v1 36 | with: 37 | username: ${{ secrets.DOCKER_USERNAME }} 38 | password: ${{ secrets.DOCKER_PASSWORD }} 39 | repository: kaylainterdonato01/createapackage 40 | tag_with_ref: true 41 | tag_with_sha: true 42 | tags: latest 43 | 44 | - name: Build pkgdown 45 | run: | 46 | PATH=$PATH:$HOME/bin/ Rscript -e 'pkgdown::build_site(".")' 47 | 48 | # deploy needs rsync? Seems so. 49 | - name: Install deploy dependencies 50 | run: | 51 | apt-get update 52 | apt-get -y install rsync 53 | 54 | - name: Deploy 🚀 55 | uses: JamesIves/github-pages-deploy-action@releases/v3 56 | with: 57 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} 58 | BRANCH: gh-pages # The branch the action should deploy to. 59 | FOLDER: docs # The folder the action should deploy. 60 | 61 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | inst/doc 2 | *~ 3 | -------------------------------------------------------------------------------- /DESCRIPTION: -------------------------------------------------------------------------------- 1 | Package: CreateAPackage 2 | Title: Material on how to create and submit a package to Bioconductor 3 | Version: 0.1.4 4 | Authors@R: c( 5 | person("Kayla", "Interdonato", role=c("aut", "cre"), 6 | email = "kayla.morrell@roswellpark.org"), 7 | person("Lori", "Shepherd", role = "aut", 8 | email = "lori.shepherd@roswellpark.org")) 9 | Description: The vignette provided has a basic sketch of the steps we 10 | ineractively will go through to build a package with devtools, explains 11 | version control with git, provides links to github, gives Bioconductor 12 | advice, and lays out the process of submitting to Bioconductor. 13 | License: Artistic-2.0 14 | Encoding: UTF-8 15 | LazyDate: true 16 | Roxygen: list(markdown = TRUE) 17 | RoxygenNote: 7.1.0 18 | Depends: devtools 19 | Suggests: knitr, 20 | rmarkdown, 21 | testthat, 22 | BiocStyle, 23 | roxygen2, 24 | pkgdown 25 | URL: https://kayla-morrell.github.io/CreateAPackage/ 26 | BugReports: https://github.com/Kayla-Morrell/CreateAPackage/issues 27 | VignetteBuilder: knitr 28 | DockerImage: kaylainterdonato01/createapackage:latest 29 | -------------------------------------------------------------------------------- /Dockerfile: -------------------------------------------------------------------------------- 1 | FROM bioconductor/bioconductor_docker:bioc2020.1 2 | 3 | WORKDIR /home/rstudio 4 | 5 | COPY --chown=rstudio:rstudio . /home/rstudio/ 6 | 7 | RUN Rscript -e "devtools::install('.', dependencies=TRUE, build_vignettes=TRUE, repos = BiocManager::repositories())" 8 | -------------------------------------------------------------------------------- /NAMESPACE: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Kayla-Morrell/CreateAPackage/4777b62f6b0e6332b968901fbc26460d24e5a560/NAMESPACE -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Create A Package 2 | 3 | # Instructor(s) name(s) and contact information 4 | 5 | * Kayla Interdonato: kayla.morrell@roswellpark.org 6 | * Lori Shepherd: lori.shepherd@roswellpark.org 7 | 8 | # Workshop Description 9 | 10 | This is a two part workshop. The first half of it will walk students through how 11 | to create a package using RStudio and the `devtools` package. This will be an 12 | instructor-led live demo, so as the student is creating their own package we 13 | will go over what we look for in Bioconductor packages. The second half of the 14 | workshop will go over the submission and review process for Bioconductor 15 | packages. 16 | 17 | ## Pre-requisites 18 | 19 | * Basic knowledge of R syntax 20 | 21 | ## Workshop Participation 22 | 23 | As the instructor creates and edits the package it is expected that students 24 | will follow along to create their own package. Questions from students are 25 | encouraged as we walk through the process, as this will most likely be their 26 | first time creating an R package. 27 | 28 | ## _R_ / _Bioconductor_ packages used 29 | 30 | * `devtools` will be used for creating, checking, documenting, and adding a 31 | vignette to the new package. 32 | * `testthat` will be used for testing the new package. 33 | 34 | ## Time outline 35 | 36 | Ideally we would prefer a 2 hour workshop, which is shown in the time outline 37 | below, but we could simplify to 1 hour if need be. 38 | 39 | | Activity | Time | 40 | |----------------------------|------| 41 | | Create a package | 5m | 42 | | Set up version control | 15m | 43 | | Description file | 10m | 44 | | R functions | 10m | 45 | | Testing | 15m | 46 | | Vignettes | 15m | 47 | | Bioconductor standards | 20m | 48 | | Submitting to Bioconductor | 15m | 49 | | Wrap up questions | 15m | 50 | 51 | # Workshop goals and objectives 52 | 53 | ## Learning goals 54 | 55 | * Understand how to create a package using RStudio and `devtools` 56 | * Understand expectations of a Bioconductor package 57 | * Understand the submission process for Bioconductor 58 | 59 | ## Learning objectives 60 | 61 | * Produce a new package 62 | * Identify Bioconductor guidelines 63 | -------------------------------------------------------------------------------- /_pkgdown.yml: -------------------------------------------------------------------------------- 1 | url: https://Kayla-Morrell.github.io/CreateAPackage 2 | 3 | template: 4 | params: 5 | bootswatch: flatly 6 | ganalytics: UA-93043521-1 7 | 8 | home: 9 | title: "CreateAPackage" 10 | type: inverse 11 | 12 | 13 | navbar: 14 | right: 15 | - icon: fa-github 16 | href: https://github.com/Kayla-Morrell/CreateAPackage 17 | 18 | 19 | -------------------------------------------------------------------------------- /vignettes/CreateAPackage.Rmd: -------------------------------------------------------------------------------- 1 | --- 2 | title: "Create A Package" 3 | author: 4 | - name: Kayla Interdonato 5 | affiliation: Roswell Park Comprehensive Cancer Center, Buffalo, NY 6 | - name: Lori Shepherd 7 | affiliation: Roswell Park Comprehensive Cancer Center, Buffalo, NY 8 | date: "`r Sys.Date()`" 9 | output: 10 | BiocStyle::html_document: 11 | toc: true 12 | toc_depth: 2 13 | vignette: > 14 | %\VignetteIndexEntry{Create A Package} 15 | %\VignetteEngine{knitr::rmarkdown} 16 | %\VignetteEncoding{UTF-8} 17 | --- 18 | 19 | # Create A Package 20 | 21 | A package is a collection of functions that work together in a cohesive manner 22 | to achieve a goal. It (should) include detailed documentation through man pages 23 | and vignettes and (should) be tested for accuracy and efficiency. [Writing R extensions](https://cran.r-project.org/doc/manuals/r-release/R-exts.html) 24 | is a very detailed manual provided by CRAN that explains writing packages and 25 | what the structure of a package should look like. This vignette is going to walk 26 | you through making your first package in RStudio as well as how to submitt a 27 | package to _Bioconductor_. 28 | 29 | ## Using `devtools` to create a package 30 | 31 | The `devtools` package provides a lot of options and utility for helping to 32 | construct a new package. You can get a list of all available `devtools` functions 33 | with `ls("package:devtools")`. 34 | 35 | Some useful references for using `devtools` to build packages are [Rstudio Devtools Cheetsheet](https://www.rstudio.com/wp-content/uploads/2015/03/devtools-cheatsheet.pdf) and [Jennifer Bryan class](http://stat545.com/packages06_foofactors-package.html). 36 | 37 | ### Package shell 38 | ```{r, eval = FALSE} 39 | library(devtools) 40 | create("myFirstPackage") 41 | ``` 42 | 43 | `create()` will _create_ all the necessary files and sub-directories that are 44 | required by R to be a valid package: DESCRIPTION, NAMESPACE, and R directory. 45 | The DESCRIPTION file contains the basic information about the package and you 46 | will have to edit so that the information is pertinent to your package. The 47 | NAMESPACE file describes which functions will be imports and exports of the 48 | namespace. The R directory will contain the R code files for your package. 49 | 50 | After running `create()`, the package has a vaild package structure which means 51 | it can be installed and loaded: 52 | 53 | * `library("myFirstPackage")`, 54 | * `library(help="myFirstPackage")`. 55 | 56 | ### Version control 57 | 58 | It is an excellent idea to version control whenever creating a package and 59 | especially when collaborating on a project, where multiple users are allowed to 60 | make changes. Version control allows for a constant recored of changes that can 61 | be advanced or reverted if necessary. 62 | 63 | Only a project can be version controlled and to make a directory a project in 64 | RStudio go to: `File -> New Project`. In this case we started creating the 65 | directory so we will follow the prompts for the option `Use Existing Directory`. 66 | Now that it is a project we can go to `Tools -> Version Control -> Project Setup` 67 | and change the `Version Control System` to `Git`, then follow the prompts. 68 | Notice in the RStudio pane for environments/history/build there is a new tab 69 | named 'Git'. The package can now start using `git` version control through 70 | making commits. To make a commit, you can go to the Git tab, select the check 71 | box next to any files that have been modified, added, or deleted that you would 72 | like to track, and select `commit`. Enter a new commit message in the window 73 | that pops up and select `commit`. 74 | 75 | It is important to tell Git just who we are. In RStudio, select `Tools -> Shell` 76 | and type the following making sure to substitue *your* user.email and user.name. 77 | If you have github we recommend using your email and user.name associated with 78 | github here. 79 | 80 | ``` 81 | git config --global user.email "" 82 | git config --global user.name "" 83 | ``` 84 | 85 | We could stop here but we also would like to put the package on GitHub. These 86 | next steps assume you have a github account. First, in RStudio go to `Tools -> 87 | Global Options` and select Git/SVN. Ensure the paths are correct. If you have 88 | not linked an RStudio project to GitHub, select `Create RSA key`. Close the 89 | window. Click on `View public key` and copy the displayed public key. Now in a 90 | web browser, open your GitHub accout. Go to `Settings` and `SSH and GPG keys`. 91 | Click on the option for `New SSH key` and paste the public key that was copied. 92 | Also on GitHub, create a new repository with the same name as the one you 93 | created with `create()` in RStudio. Back in RStudio, select `Tools -> Shell` and 94 | type the following making usre to substitue your GitHub user.name and the new 95 | package name. 96 | 97 | ``` 98 | git remote add origin https://github.com//.git 99 | git remote set-url origin git@github.com:/.git 100 | git pull origin master 101 | git push -u origin master 102 | ``` 103 | 104 | For instance, this is what the commands would look like for me: 105 | 106 | ``` 107 | git remote add origin https://github.com/Kayla-Morrell/myFirstPackage.git 108 | git remote set-url origin git@github.com:Kayla-Morrell/myFirstPackage.git 109 | git pull origin master 110 | git push -u origin master 111 | ``` 112 | 113 | The `git remote add` command will create a new connection to the remote 114 | repository url and assign it the shortname 'origin' for easy referencing moving 115 | forward. Then the `git remote set-url` command is going to switch the 116 | url of the remote from 'https', which is public read only access, to 'SSH' so 117 | that you as a developer can have read and write access to the repository. `git 118 | pull` is going to fetch and download content from the remote repository and 119 | update the local repository to match. `git push` does the exact opposite, it 120 | will upload the local repo changes to the remote repo. 121 | 122 | Now if you look in the RStudio tab for Git, the push and pull options are 123 | available. You can now push and pull from/to the local and GitHub repository 124 | version of your package. 125 | 126 | ## DESCRIPTION file 127 | 128 | `devtools` provides built in functions for building, checking and installing a 129 | package. The package we created earlier using `create()` has a valid package 130 | structure but if we did `check()` we will find the DESCRIPTION file needs to be 131 | updated. The information in the DESCRIPTION file needs to be reflective of your 132 | package. These are the fields that should be changed: 133 | 134 | * Title: Should be brief, but descriptive. 135 | * Version: Should be 0.99.0 for pre-release packages. 136 | * Authors@R: Only one person should be listed as maintainer (`cre`). We do 137 | accept Author/Maintainer for this field, either can be used but not both. 138 | * Description: Should be relatively short but a detailed overview of what the 139 | package functionality entails. 140 | * License: Preferably a standard license, Bioconductor core packages typically 141 | use Artistic-2.0. If using a non-standard license, must include a LICENSE file 142 | in your package and use `file LICENSE` in this field. 143 | * LazyData: Should be set to false, we find that this field being true can slow 144 | down the loading of a package especially if it contains large data. 145 | 146 | Throughout the development of your package you may have to update the 147 | DESCRIPTION file for appropriate Depends, Imports, and Suggests fields as you 148 | incorporate more functionality from other packages. As the package is developing 149 | we also require having a `biocViews:` field in the DESCRIPTION file. This field 150 | will contain at least two biocViews categories that reflect the nature of the 151 | package. 152 | 153 | ## R functions 154 | 155 | Now we want to starting writing R functions. In RStudio you can open an empty 156 | file by doing `File -> New File` and selecting `R Script`. Save the file in the 157 | R directory. Write your functions and document. You can either document 158 | functions manually or if you use roxygen you can use the devetools function 159 | `document()`. See the [Writing R extensions](https://cran.r-project.org/doc/manuals/r-release/R-exts.html) 160 | for manual creation of Rd files, which belong in the man directory, but roxygen 161 | is growing increasingly popular. Some helpful links for roxygen tags can be 162 | found at [RStudio Devtools Cheatsheet](https://www.rstudio.com/wp-content/uploads/2015/03/devtools-cheatsheet.pdf) and 163 | [Roxygen Help](https://cran.rstudio.com/web/packages/roxygen2/vignettes/rd.html). 164 | 165 | Some useful `devtools` commands while creating functions are: 166 | 167 | * `load_all()` which loads all package functions in environment to test, 168 | * `check()` which checks the package (R CMD check), 169 | * `document()` which generates or updates any documentation files. 170 | 171 | Using the RStudio options `Build -> Build and Reload` and `Build -> Clean 172 | and Rebuild` will also help with function creation. 173 | 174 | It is also recommended to have a man page for you package. `devtools` provides 175 | a framework for this. To create the file that needs to be modified use the 176 | function `use_package_doc()`. 177 | 178 | If you import any functions in your code, don't forget to update the DESCRIPTION 179 | file for Depends, Imports, or Suggests. If the function provides essential 180 | functionality for users of your package, it belongs in Depends. It is unusual 181 | for more than three packages to be listed as Depends. For packages that provide 182 | functions, methods, or classes that are used inside your package namespace, they 183 | belong in Imports. Most packages will be listed here. For packages that are used 184 | in vignettes, examples, or conditional code, they should be listed as Suggests. 185 | This includes examples that may use annotation and/or experiment packages. 186 | 187 | ## Testing 188 | 189 | It is highly recommened to add unit tests to your package. Unit tests unsure 190 | that the package is working as expected. The two main ways to test are using 191 | `RUnit` or `testthat`. `testthat` functionality is included in `devtools` by 192 | using `use_testthat()`. This function will set up the needed directory structure 193 | and add the package suggestion to the DESCRIPTION file. Here are some examples 194 | of the structure of tests for `testthat`: 195 | 196 | * `expect_identical()`, 197 | * `expect_true()`, 198 | * `expect_error()`. 199 | 200 | There are other options as well that are discussed in [testthat Wickham](https://journal.r-project.org/archive/2011-1/RJournal_2011-1_Wickham.pdf) and [testthat](http://r-pkgs.had.co.nz/tests.html). 201 | 202 | ## Vignettes 203 | 204 | Vignettes are another major documentation piece to a package. More and more 205 | repository systems (CRAN, Bioconductor, ROpenSci) are making vignettes a 206 | standard requirement. Vignettes are contain a more indepth description and 207 | examples of the package usage. `devtools` also provides the function 208 | `use_vignette()` to set up the directory structure and the initial file for 209 | a vignette. For Bioconductor submissions we recommend changing the `output:` 210 | section for the vignette header to the following, which would require adding 211 | `BiocStyle` to the Suggests field in the DESCRIPTION file, 212 | 213 | ``` 214 | output: 215 | BiocStyle::html_document: 216 | toc: true 217 | toc_depth: 2 218 | ``` 219 | 220 | Or if `BiocStyle` is already installed on your system, you can also use RStudio 221 | to set up the vignette by doing `New File -> Rmarkdown -> From Template -> 222 | Bioconductor HTML/PDF Vignette`. 223 | 224 | A helpful rmarkdown link, which is commonly used for vignette creation, can be 225 | found here: [rmarkdown cheatsheet](http://www.rstudio.com/wp-content/uploads/2016/03/rmarkdown-cheatsheet-2.0.pdf). 226 | 227 | ### Bioconductor Standards 228 | 229 | Now that we have gone over the basics of how to create a package, we will review 230 | what we look for (generally) in Bioconductor packages. Being mindful of these 231 | guidelines while developing your package will help the whole submission process. 232 | 233 | 1. Proper coding and efficient coding: 234 | 235 | * [Efficient and Robust Code](http://bioconductor.org/developers/how-to/efficient-code/) 236 | * [Query Web Resource](http://bioconductor.org/developers/how-to/web-query/) 237 | 238 | 2. Bioconductor interconnectivity and S4 classes 239 | 240 | * S4 over S3 classes 241 | * Reuse existing infrastructure first! 242 | + DNA/RNA - `Biostrings` `DNAstringset` 243 | + Gene sets - `GSEABase` `GeneSet` 244 | + Genomic intervals - `GenomicRanges` `Granges` 245 | + Rectangular feature x sample data - (RNAseq count matrix, microarray) - 246 | `SummarizedExperiment`/`MuliAssayExperiment` 247 | + Single cell - `SingleCellExperiment` 248 | + Mass spec - `MSnbase` 249 | + import/loading data 250 | - GTF, GFF, BED, BigWig, ... `rtracklayer::import()` 251 | - FASTA `Biostrings::readDNAStringSet()` 252 | - SAM/BAM `Rsamtools::scanBam()`, `GenomicAlignments::readGAlignment*()` 253 | - VCF `VariantAnnotation::readVcf()` 254 | - FASTQ `ShortRead::readFastq()` 255 | * [BiocViews](http://bioconductor.org/packages/release/BiocViews.html#___Software) 256 | 257 | 3. Tests 258 | 259 | * [Unit test guidelines](http://bioconductor.org/developers/how-to/unitTesting-guidelines/) 260 | 261 | 4. Complete and detailed vignette(s) and man pages, with executable examples 262 | 263 | 5. Check time < 5 minutes 264 | 265 | 6. Package size < 5Mb 266 | 267 | 7. All package guidelines can be found [here](http://bioconductor.org/developers/package-guidelines/) 268 | 269 | **IMPORTANT**: A clean build, check, and BiocCheck is not a guaranteed acceptance. 270 | The package will still go through a formal review process. 271 | 272 | ### Submitting to Bioconductor 273 | 274 | Be sure to read the [Contributions Page](https://github.com/Bioconductor/Contributions) and 275 | when you are ready to submit open a [New Issue](https://github.com/Bioconductor/Contributions/issues). 276 | The Title: should be the name of your package. Once the package is approved for 277 | building, don't forget to set up the [remotes](https://bioconductor.org/developers/how-to/git/new-package-workflow/). 278 | Some details about the review process can be found [here](http://bioconductor.org/developers/package-submission/#whattoexpect). 279 | --------------------------------------------------------------------------------