Configuring Jekyll for github PROJECT pages
When you have a slash at the front of your permalink, it means that all URLs should be relative to the site root. This is the reason that it's going to http://corroded.github.com/exercises/title-here
instead of http://corroded.github.com/projectname/exercises/title-here
. Try it without the first slash:
permalink: exercises/:title
The same thing goes for any URLs you create with HTML. If you have:
<a href="/about">
it will always go to the root of the domain (e.g. http://corroded.github.com/about
). If you're project is called 'projectname', you can use HTML like
<a href="/projectname/about">
to link directly to pages (e.g. http://corroded.github.com/projectname/about
).
Of course, you can also use relative URLs (i.e. URLs without a leading slash) as well. You just have to be aware of where you are in the directory tree.
How to use theme from github.io site for Github Project Pages sites
Yesterday I finally went through and did what I theorized about in September. The result lives here now. This was not an easy process, despite the documentation trying to be helpful, because the intersection of Jekyll and GitHub pages is such a massively complicated opaque box, and ruby was unfamiliar to me. But ultimately it boils down to a few important steps and gotchas:
You're gonna need ruby and several packages.
sudo apt install ruby
should give youruby
(interpreter) andgem
(package manager).- Gotcha 1a: The basics are left unexplained, so allow me: Ruby code comes in packages called gems, which are a lot like python packages. They're managed by
gem
orbundler
rather thanpip
and hosted onrubygems.org
instead ofpypi
. Much like in the Python world where everyone sings the praises ofconda
, everyone in the Ruby world sings the praises ofbundler
, which is itself a gem, one that you have togem install
because it doesn't come packaged with ruby likegem
itself. I found bundler to be buggy; it hung when I tried tobundle install github-pages
(more ongithub-pages
later). Also, bundler relies on yet more configuration files calledGemfile
s, which are the analog of therequirements.txt
filespip
can but doesn't need to ingest. Honestly who wants more of that clutter lying around for a small project with no complicated dependency tree? And who wants to have tobundle exec jekyll serve
instead of justjekyll serve
? Are you kidding me? Just usegem
to install things, and skip theGemfile
. Much likepip
, I find simpler is better. - Gotcha 1b: If you
sudo apt install jekyll
, you get an old version, like 3.1 or something. But Jekyll is a gem; you can and should install using the package manager. (But actually don't do this, because it comes as part of thegithub-pages
gem, and the versions don't agree. More on that later.) - Gotcha 1c: Oh, what's that? You want to
gem install jekyll
(or evengem install bundler
)? Yeah, sorry, I can't do that because there's some stuff missing, and here's a long printout about it. ...Google, Google...sudo apt install ruby-dev
. Oh, sorry I still can't build. Here are some other errors. ...Google, Google...sudo apt install g++
. Okay now it works. This process might be slightly different for you; point is setting up a ruby environment can be dicey. - Gotcha 1d: Oh what's that? Now you want to be able to call
jekyll
from the command line like you could if you just installed it withapt
? Well, sorry, I'mgem
, and some times I don't putjekyll
on your path. If this happens to you, pay attention to wheregem
saves the gems, go find the executable within, and then create a symlink withsudo ln -s /path/to/jekyll /usr/bin/jekyll
- Gotcha 1a: The basics are left unexplained, so allow me: Ruby code comes in packages called gems, which are a lot like python packages. They're managed by
Move
assets
,_includes
,_layouts
, and_sass
from the site to a new repo. Done. Bam. You have a remote theme now. It really should be that easy, but...- Gotcha 2a: No one tells you that's the minimum viable product, so you have to start by understanding what remote themes are and how they work. According to canon, they're full-blown gems. When you reference one, Jekyll needs to go and fetch it before it can generate your site. The Jekyll documentation is all about coaching you on how to truly package up your theme as a gem and push it up to
rubygems.org
, which requires: (1) a rubygems account, (2) for your theme to contain an abstruse.gemspec
file, the contents of which are not well explained. Keep reading for why this is irrelevant. - Gotcha 2b: You have to understand how GitHub Pages actually uses remote themes. On this topic GitHub is happy to tell you about adding
remote_theme: user/theme-name
to the leveraging site's_config.yml
(Jekyll config), but they neglect to tell you upfront whether they're pulling in a gem from somewhere or what. Turns out they're using yet another gem calledjekyll-remote-theme
to pull the raw files directly from a repo, making the step of compiling and uploading a gem and having a.gemspec
no one understands or wants to look at unnecessary. (Hooray.) benbalter's documentation for the remote theme gem itself is the only place I could find this information. - Gotcha 2c: Beware that because Pages is still on Jekyll 3.8.6, you don't have certain functionality on GitHub Pages that you might want, like being able to define site data in the theme's
_config.yml
. As a result, my front-matter-prepended.css
containing a few Liquid tags that worked just fine as part of my unseparated site ended up with emptystring tag substitutions in the generated site. I ended up hard-coding some variables in the theme. - Gotcha 2d: Any other folders and files--not among
assets
,_includes
,_layouts
, and_sass
--(I had one namedtheme
containing stuff like my favicon.) don't get folded in to a theme gem or transported via thejekyll-remote-theme
mechanism employed by GitHub. By carefully amending the.gemspec
, you can include those files in a gem, but this method has no effect on the behavior ofjekyll-remote-theme
, so I ended up basically putting everything inassets
. - Complaint 2e: Ruby Sass is apparently deprecated now? Why has Jekyll continued to use it for so long? I've still not encountered an example where it seems useful.
- Gotcha 2a: No one tells you that's the minimum viable product, so you have to start by understanding what remote themes are and how they work. According to canon, they're full-blown gems. When you reference one, Jekyll needs to go and fetch it before it can generate your site. The Jekyll documentation is all about coaching you on how to truly package up your theme as a gem and push it up to
Put a
_config.yml
containingremote_theme: yourname/yourtheme
in the root directory of thegh-pages
branch of every repo for which you want the Project Pages rendered in your theme. No Gemfile, no nonsense. Just wait for it to deploy.- Gotcha 3a: Jekyll looks specifically for a
page.html
file inside_layouts
to renderreadme
contents. If you have apage.html
, then you can add your head, navbar and other_includes
stuff to it with Liquid tags no problem. If you happened to forget this file or think Jekyll could usepost.html
instead, well then you'd be wrong, and the theme isn't applied. Not sure whetherdefault.html
would work as a failover. In any case, GitHub pages with Jekyll is super brittle, and I'm honestly lucky to have discovered this without being blocked by it, because (1) I haven't seen any GitHub documentation to describe exactly which commands are being called to generate Project Pages, (2) you can't see the terminal output for the remote compilation process**, and (3), because you don't know what GitHub is doing, there is no way to replicate it locally to see warnings or error printouts--that is if Jekyll even warns you about this.
**If there actually is a way to view this somewhere, please tell me. GitHub says: "When you push changes to your publishing source on GitHub, GitHub Pages will attempt to build your site. If the build fails, you'll receive an email at your primary email address. You'll also receive emails for build warnings. You can see build failures (but not build warnings) for your site on GitHub in the Settings tab of your site's repository." I did receive an email stating "The taginclude_cached
on line 15 in/_layouts/default.html
is not a recognized Liquid tag.", but I don't remember which build this was for, and I can't find the failure recorded in the repo Settings anywhere. - Gotcha 3b: If you update the theme, Pages sites which use the theme aren't rebuilt to reflect the theme changes. You have to manually repush to the branch a site is built from to trigger a site rebuild. This is pretty easy for repos I've integrated with Travis-CI, because I can just go down the list rerunning the most recent builds, which culminate in pushes to
gh-pages
branches, which in turn cause Pages servers to rebuild. But for other sites, I have to either make some legitimate change or push an empty commit.
- Gotcha 3a: Jekyll looks specifically for a
Add
plugins: - jekyll-remote-theme
andremote_theme: yourname/yourtheme
to the_config.yml
in your User Pages site.- Gotcha 4a: Local execution is confusing. benbalter's readme is pretty good, but the Usage section still assumes you're using
bundler
. If you're not, thengem install github-pages
like you'd install any other gem. This gem is really a huge list of other gems Pages servers actually run to generate your static site, including the same versions ofjekyll
andjekyll-remote-theme
. You'll want these so you can catch all subtle version or display bugs locally and have no surprises in the cloud. Finally, despite it not seeming to be necessary for actual deployment, for local execution you have to make sure to listjekyll-remote-theme
as a plugin in your leveraging site's_config.yml
. Otherwisejekyll serve
errors. - Gotcha 4b: Local execution with a remote theme is broken--or at least it is for Jekyll 4.0.0. It works fine for Jekyll 3, which is what GitHub Pages servers use, which is why it deploys fine. If you get Jekyll with
gem install jekyll
rather than from thegithub-pages
list, you might get errors as I did.
- Gotcha 4a: Local execution is confusing. benbalter's readme is pretty good, but the Usage section still assumes you're using
So basically it's not hard in hindsight, but getting there is a frustrating fiasco of flying blind with only overly verbose, disappointingly incomplete maps to guide you. I wish GitHub would show you the whole process of site compilation and deployment in some terminal, like Travis-CI does for builds. And I wish Jekyll weren't so complicated. There are too many features, and too many things fail silently.
I hope this research can help somebody else.
How do I configure GitHub to use non-supported Jekyll site plugins?
Depending if you deal with a User/Organization (UO) site or a Project site (P), do :
- from your working folder
git init
git remote add origin git@github.com:userName/userName.github.io.git
(UO) orgit remote add origin git@github.com:userName/repositoryName.git
(P)jekyll new .
creates your code base- in _config.yml, set the baseurl parameter to
baseurl: ''
(UO) orbaseurl: '/repositoryName'
(P) - in .gitignore add _site, it will be versioned in the other branch
jekyll build
will create the destination folder and build site.git checkout -b sources
(UO) orgit checkout master
(P)git add -A
git commit -m "jekyll base sources"
commit your source codegit push origin sources
(UO) orgit push origin master
(P) push your sources in the appropriate branchcd _site
touch .nojekyll
, this file tells gh-pages that there is no need to buildgit init
init the repositorygit remote add origin git@github.com:userName/userName.github.io.git
(UO) orgit remote add origin git@github.com:userName/repositoryName.git
(P)git checkout master
(UO) orgit checkout -b gh-pages
(P) put this repository on the appropriate branchgit add -A
git commit -m "jekyll first build"
commit your site codegit push origin master
(UO) orgit push origin gh-pages
(P)
You now have something like Octopress does. Look at their rake file, there are some nice comments inside.
Configure GitHub Pages syntax highlighting identical to GitHub
GitHub uses a closed syntax highlighting library not available on GitHub Pages. Supposedly, it should be possible to get a reasonable result using the default Jekyll highlighter. However, for me it was simpler to switch to the highlight.js JS library. Here are the steps.
Disable Jekyll's highlighter in the _config.yml
Obtain the highlight.min.js library
- Prebuilt library is available from the website or via CDNs.
- A custom version can be generated online, if necessary.
Obtain a CSS theme file
Specific CSS theme can be picked chosen using online demo service. CSS files are also available via CDNs or can be downloaded for local access.Load the library, theme file, and initialize the library
In my case, I placed the library in /assets/js/highlight.min.js and included the following lines in /_includes/head_custom.html
<link rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/highlight.js/11.6.0/styles/github.min.css">
<script type="text/javascript" src="{{ '/assets/js/highlight.min.js' | relative_url }}"></script>
<script>hljs.highlightAll();</script>
I also included a CSS element /_sass/custom/custom.scss in to overwrite code block background:
.hljs {background: #fdfdfa !important;}
Setting Jekyll environment for GitHub Pages
After a lot of trial and error, I finally figured out how to fix this issue. For whatever reason, the answer provided by @Christian Specht (using two different config files wasn't working). Instead I had to manually change the environments using the child process spawns
in my gulp tasks. My updated gulpfile.js
:
/**
* Build the Jekyll Site
*/
gulp.task('jekyll-build', function (done) {
browserSync.notify(messages.jekyllBuild);
return cp.spawn('jekyll', ['build'], { stdio: 'inherit' })
.on('close', done);
});
/**
* Build the Jekyll Site for production
*/
gulp.task('jekyll-build-prod', function (done) {
browserSync.notify(messages.jekyllBuild);
var productionEnv = process.env;
productionEnv.JEKYLL_ENV = 'production';
return cp.spawn('jekyll', ['build'], { stdio: 'inherit' , env:productionEnv })
.on('close', done);
});
/**
* Deploy to gh-pages
*/
gulp.task('deploy', ['jekyll-build-prod'], function() {
return gulp.src('./_site/**/*')
.pipe(ghPages());
});
GitHub pages serving from docs and jekyll source folder config
Is Jekyll's documentation unclear. Yes.
New github pages publication branch/folder :
Available options are (doc) :
- gh-pages branch
- master branch
- master branch /docs folder
- Disable GitHub Pages.
Three first options defines your root publication folder.
Github pages uses this root folder to generate your site. You cannot override source
key in your _config.yml
.
Your can store your sources in a _docs folder and output in docs
- project
| - _docs
| | content
| | files
| | tools
|
| - docs << output here
Related Topics
Can't Convert Fixnum to String During Rake Db:Create
How to Get a List of All Tags While Using the Gem 'Acts-As-Taggable-On' in Rails (Not the Counts)
How to Render a Partial in Sinatra View (Haml in Haml)
Best Way to Cache a Response in Sinatra
What's the Best Way to Parse a Tab-Delimited File in Ruby
How to Set a Blank Value for an F.Select Form Field
How to Check If a Gem Is Installed
Listing the Names of Associated Models
Rails Activeadmin - Custom Association Select Box
Checking If a Method Is Defined on the Class
Anybody Tried the Crystal Programming Language (Machine-Code Compiled Ruby)
Ruby: Get All Keys in a Hash (Including Sub Keys)
How to Introspect Things in Ruby
Activerecord Objects in Hashes Aren't Garbage Collected -- a Bug or a Sort of Caching Feature