Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update GitHub Pages section #1218

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
115 changes: 88 additions & 27 deletions inst/examples/06-publishing.Rmd
Original file line number Diff line number Diff line change
Expand Up @@ -19,42 +19,103 @@ bookdown::publish_book(render = 'local')

If you have set up your own RStudio Connect server, you can certainly publish the book to that server instead of bookdown.org.

## GitHub
## GitHub Pages {#github}

You can host your book on GitHub\index{GitHub} for free via GitHub Pages (https://pages.github.com). GitHub supports Jekyll (http://jekyllrb.com), a static website builder, to build a website from Markdown files. That may be the more common use case of GitHub Pages, but GitHub also supports arbitrary static HTML files, so you can just host the HTML output files of your book on GitHub. The key is to create a hidden file `.nojekyll` that tells GitHub that your website is not to be built via Jekyll, since the **bookdown** HTML output is already a standalone website.
You can host your book on GitHub\index{GitHub} for free via GitHub Pages (<https://pages.github.com>).^[See the [GitHub Pages Help documents](http://bit.ly/2cvloKV) for more information.] The simplest approach is to publish your book as a [GitHub Project Page](https://help.github.com/en/articles/user-organization-and-project-pages#project-pages-sites) from a `/docs` folder on your `main` branch, which will then be available at `https://<USER>.github.io/<REPO>` (unless you provide a custom domain name). The main benefit to this approach is its simplicity, and the fact that you can track the source files for your book and the published HTML files in the same branch.
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this the preferred way all the time compared to gh-pages ?
Or is this what you think is simpler to use with Bookdown ?

My view on this:

  • /docs folder is simpler when not using a CI:

    • Build locally to docs/
    • Commit and push
  • I find gh-pages cleaner to have in the source repo and easier to put in place when using a CI. Locally I use a Makefile to help me generally

    • On main branch, _book (or other output dir) is in .gitignore
    • I build the book locally
    • Then I switch branch to gh-pages
    • I commit the _book folder
    • I push the gh-pages branch
    • I switched back to main branch

Makefile do all that for me usually. Using a R file with gert should use the same. An R function could help with that.

Anyway, just sharing how I work with this.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would definitely suggest the gh-pages route for folks who are comfortable with Make, gert, and CI systems like GHA (like yourself). I can draft that section, but could use a draft GHA workflow (much easier than Make/gert) since there is no deploy_to_branch() :)

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok so we agree on this.

I suggest we do the GHA part later - this would require to rework a bit a workflow, and I would like to show netlify and rstudio connect for all options. Best would be to have demo repo too with all this !
So it is a bit of work to it right IMO.

It is also possible to work on helper function to help deploy. We have already publish_book() for rstudio connect, we could have another one for GH Pages deployement (but it could also be directly in the Workflow template).

I can work ont that... but later in another PR.

How does that sounds ?


```bash
# assume you have initialized the git repository,
# and are under the directory of the book repository now
### The build-and-deploy pipeline sequence

# create a hidden file .nojekyll
touch .nojekyll
# add to git here because will not show up in RStudio
git add .nojekyll
```
This publishing approach sets up the following flow of events:

If you are on Windows, you may not have the `touch` command, and you can create the file in R using `file.create('.nojekyll')`.
1. You create a local **bookdown** project in a GIT repository that is connected to a GitHub repository. The below steps assume you are on your `main` branch.
1. You change the output directory of your rendered book to a folder named `"docs"`.
1. You tell GitHub Pages to bypass using Jekyll to build your site.
1. You build your book locally, then push to send your local changes online to GitHub.
1. The push to the `main` branch triggers GitHub Pages to publish your book at: `https://<USER>.github.io/<REPO>`.
1. Rinse and repeat! Every push to `main` triggers the online version of your book to update.

One approach is to publish your book as a GitHub Pages site from a `/docs` folder on your `master` branch as described in [GitHub Help.](http://bit.ly/2cvloKV) First, set the output directory of your book to be `/docs` by adding the line `output_dir: "docs"` to the configuration file `_bookdown.yml`. Then, after pushing your changes to GitHub, go to your repository's settings and under "GitHub Pages" change the "Source" to be "master branch /docs folder". In this case, the `.nojekyll` file has to be in the `/docs` folder.
The above is an overview- read on for step-by-step instructions.

An alternative approach is to create a `gh-pages` branch in your repository, build the book, put the HTML output (including all external resources like images, CSS, and JavaScript files) in this branch, and push the branch to the remote repository. If your book repository does not have the `gh-pages` branch, you may use the following commands to create one:
### Before you begin

```bash
# assume you have initialized the git repository,
# and are under the directory of the book repository now
1. You need a GitHub (<https://github.com/>) account.^[If you are not familiar with GitHub, we suggest you read through the free online book "Happy Git with R" (<https://happygitwithr.com/>) first before working through these instructions.]

1. Start with a **bookdown** project linked to a remote GitHub repository that you can push/pull to from your local copy.

:::{.rmdimportant latex=true}

If you don't have an existing book, you can create a simple **bookdown** HTML book to practice with instead:

# create a branch named gh-pages and clean up everything
git checkout --orphan gh-pages
git rm -rf .
+ Make a new repository on GitHub (<https://happygitwithr.com/new-github-first.html#make-a-repo-on-github-2>),
+ Make a new RStudio Project via git clone: (<https://happygitwithr.com/new-github-first.html#new-rstudio-project-via-git-clone>),
+ From your RStudio Project, run this command in your R console: `bookdown::create_gitbook()` or `bookdown::create_bs4_book()` (depending on the HTML output format you want),
+ Change anything you want (or change nothing) and commit (<https://happygitwithr.com/new-github-first.html#make-local-changes-save-commit-1>),
+ Push your local changes to GitHub (<https://happygitwithr.com/new-github-first.html#push-your-local-changes-to-github>).

# create a hidden file .nojekyll
touch .nojekyll
git add .nojekyll
:::

git commit -m"Initial commit"
git push origin gh-pages

### Change the output directory of your book

In your local **bookdown** project, open the `_bookdown.yml` file and change the output directory of your book to be `/docs` by adding this line:

```yaml
output_dir: "docs"
```

Save this file and close it.

### Tell GitHub Pages to bypass Jekyll

Create a hidden, empty file named `.nojekyll` from within R in your **bookdown** project root directory:

```
file.create(".nojekyll")
```

If you are using RStudio, you may need to refresh the viewer pane to see this new file. You can also use the terminal to create this file with the command `touch .nojekyll`.

This file is [necessary](https://github.blog/2009-12-29-bypassing-jekyll-on-github-pages/) because GitHub Pages supports Jekyll ([jekyllrb.com](http://jekyllrb.com)), a static website builder, by default. You need the `.nojekyll` file because bookdown sites uses files or directories that start with underscores, and these files have a special status within the Jekyll framework. Because the **bookdown** HTML output is a static, standalone website, you need to tell GitHub that your website should *not* be built via Jekyll.
Comment on lines +68 to +78
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is where the file needs to be inside the /docs folder.

So it should be file.create("docs/.nojekyll") in your example. And docs/ should not be cleaned, otherwise the file would need to be restored.

Other solution would be to create the file at build time, but this currently needs a hack because the file is not moved automatically to output dir. See #1190 (comment)

This is why we need to provide a better way.

I would advice your solution for now creating in the right directory. As it will be tracked by Git, a user would quickly see if this will is to be deleted during a cleaning.

Note on cleaning: You need to clean you book output dir sometimes when working on a book because bookdown won't do that for you. There could be some conflicts sometimes. For example: You work on a chapter, you build, you commit, you are not happy and change the structure of the book which will lead to new html file name because new chapters. The old chapter does not exist anymore, but the HTML files still are. You will commit the new ones but it will not necessarily overwrite the old ones if the names are different. You will have old HTML files in your published book. For this a cleaning is required before rebuilding the book.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Got it, I was thinking that was not going to work but then re-read the existing section (https://bookdown.org/yihui/bookdown/github.html) and thought I was wrong.


### Build your book, push to GitHub

Use whichever method from Chapter \@ref(build-the-book) you prefer, then push to send your local changes online to GitHub.

:::{.rmdwarning latex=true}

If you have previously added directories like `_book` and `_bookdown_files` to your remote GitHub repository, you'll want to take a few more steps to remove them:

* Delete the folders locally

* From the terminal:
* `git rm -r --cache _book/`
* `git rm -r --cache _bookdown_files/`
* `git commit -m 'Remove the rendered book files'`
* `git push origin main`

:::
Comment on lines +84 to +96
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think in this case you also want to delete them locally, at least _book, isn't it ?

Your new book will be in docs/.

But I guess it is easier for a user to do that itself than knowing how to remove from git.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was told by several on the tidyverse team that you had to do both (which is what this says)- so you mean only do step 1?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No no what I am saying is that git rm -r --cache _book/ will not delete the _book folder.
It will still be there but untracked. If you don't need it anymore (because you are using docs/ now, it should be removed I think (bookdown::clean_book(TRUE))

For _bookdown_files, I don't remember what it is used for. Doing git rm -r --cache _bookdown_files/ will untrack eveything from Git, but the files will still be there on the system.

I wasn't sure here if we are supposed to keep those or not.

Anyway, if those command where proven useful in the past, then it is the right one to switch. Usually I would set up at the start of a project, so I don't really try to undo stuff. But just start fresh.

Meaning:

  • bookdown::clean_book(TRUE) => start fresh bookdown project
  • change config output_dir and other stuff
  • bookdown::render_book()
  • Commit everything (new stuff and also result of first step deletion.)

The only time I am using git rm -r --cache if I am right is when I want to untrack something without deleting it in my worktree because I want to now ignore it in the future



### GitHub Pages Setup

In a browser, navigate to your repository on GitHub at `https://github.com/<USER>/<REPO>`. Then:

1. Confirm that you see a `/docs` folder and a `.nojekyll` file.

1. Navigate to the repository's settings at `https://github.com/<USER>/<REPO>/settings/pages` and under *Pages* and change the *Source* to be the `main` branch and the `/docs` folder (check the box to enforce HTTPS):

```{r github-pages, echo=FALSE, fig.align='center', fig.alt="Screenshot of selecting main branch `/docs` folder for GitHub Pages"}
knitr::include_graphics("images/ghpages.png")
```

1. Save, and then wait. It can sometimes take quite awhile (even up to 20 minutes) for your site link to work. Be patient!

### Drawbacks and alternatives

The main drawback to this approach is that you store the rendered book (i.e., the `/docs` folder) on GitHub in your `main` branch. Although it is relatively straight-forward approach to publish your book from a folder on your `main` branch, it means that you always need to build the book locally first, then push to send the built book online to GitHub. It can be very handy to instead automate the publishing process even more by building the book using a cloud service. Once set up, all you have to do is edit the `.Rmd` source files and push them to GitHub, and your book will be automatically built and published from the server side.

## Using Travis

After you have set up GIT, the rest of work can be automated via a script (Shell, R, or Makefile, depending on your preference). Basically, you compile the book to HTML, then run git commands to push the files to GitHub, but you probably do not want to do this over and over again manually and locally. It can be very handy to automate the publishing process completely on the cloud, so once it is set up correctly, all you have to do next is write the book and push the Rmd source files to GitHub, and your book will always be automatically built and published from the server side.

One service that you can utilize is Travis CI (https://travis-ci.com).\index{Travis CI} It is free for public repositories on GitHub, and was designed for continuous integration (CI) of software packages. Travis CI can be connected to GitHub in the sense that whenever you push to GitHub, Travis can be triggered to run certain commands/scripts on the latest version of your repository.^[You need to authorize the Travis CI service for your repository on GitHub first. See https://docs.travis-ci.com/user/getting-started/ for how to get started with Travis CI.] These commands are specified in a YAML file named `.travis.yml` in the root directory of your repository, and they are usually for the purpose of testing software, but in fact they are quite open-ended, meaning that you can run arbitrary commands on a Travis (virtual) machine. That means you can certainly run your own scripts to build your book on Travis. Note that Travis only supports Ubuntu and Mac OS X at the moment, so you should have some basic knowledge about Linux/Unix commands.
Expand All @@ -66,7 +127,7 @@ The next question is, how to publish the book built on Travis to GitHub? Basical
e.g `travis encrypt GITHUB_PAT=TOKEN`. If you do not know how to install or use the Travis command-line tool, simply save this environment variable via https://travis-ci.com/user/repo/settings where `user` is your GitHub ID, and `repo` is the name of the repository.
1. You can clone this `gh-pages` branch on Travis using your GitHub token, add the HTML output files from R Markdown (do not forget to add figures and CSS style files as well), and push to the remote repository.

Assume you are in the `master` branch right now (where you put the Rmd source files), and have compiled the book to the `_book` directory. What you can do next on Travis is:
Assume you are in the `main` branch right now (where you put the Rmd source files), and have compiled the book to the `_book` directory. What you can do next on Travis is:

```bash
# configure your name and email if you have not done so
Expand All @@ -85,7 +146,7 @@ git commit -m"Update the book"
git push -q origin gh-pages
```

The variable name `GITHUB_PAT` and the directory name `book-output` are arbitrary, and you can use any names you prefer, as long as the names do not conflict with existing environment variable names or directory names. This script, together with the build script we mentioned in Section \@ref(build-the-book), can be put in the `master` branch as Shell scripts, e.g., you can name them as `_build.sh` and `_deploy.sh`. Then your `.travis.yml` may look like this:
The variable name `GITHUB_PAT` and the directory name `book-output` are arbitrary, and you can use any names you prefer, as long as the names do not conflict with existing environment variable names or directory names. This script, together with the build script we mentioned in Section \@ref(build-the-book), can be put in the `main` branch as Shell scripts, e.g., you can name them as `_build.sh` and `_deploy.sh`. Then your `.travis.yml` may look like this:

```yaml
language: r
Expand Down Expand Up @@ -231,4 +292,4 @@ The book was compiled to PDF through `xelatex` to make it easier for us to use c

All above settings except the `VF` environment and the `\VA{}` command can be applied to any other LaTeX document classes.

In case you want to work with Chapman & Hall as well, you may start with the copy of `krantz.cls` in our repository (https://github.com/rstudio/bookdown/tree/master/inst/examples) instead of the copy you get from your editor. We have worked with the LaTeX help desk to fix quite a few issues with this LaTeX class, so hopefully it will work well for your book if you use **bookdown**.
In case you want to work with Chapman & Hall as well, you may start with the copy of `krantz.cls` in our repository (https://github.com/rstudio/bookdown/tree/main/inst/examples) instead of the copy you get from your editor. We have worked with the LaTeX help desk to fix quite a few issues with this LaTeX class, so hopefully it will work well for your book if you use **bookdown**.
Binary file added inst/examples/images/ghpages.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.