Skip to content
Merged
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
3 changes: 0 additions & 3 deletions _config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -73,17 +73,14 @@ defaults:
path: 'content/_en'
values:
lang: en
base_path: ''
- scope:
path: 'content/_es'
values:
lang: es
base_path: /es
- scope:
path: 'content/_fr'
values:
lang: fr
base_path: /fr

include:
# dotfiles are excluded by default
Expand Down
21 changes: 1 addition & 20 deletions _includes/language_picker.html
Original file line number Diff line number Diff line change
Expand Up @@ -24,26 +24,7 @@
>
{% for locale in site.languages %}
<li>
{% if page.lang == 'en' %}
{% if locale == 'en' %}
{% assign locale_url = page.url %}
{% elsif locale == page.lang %}
{% assign locale_url = page.url %}
{% else %}
{% assign locale_url = page.url | prepend: locale | prepend: '/' %}
{% endif %}
{% else %}
{% if locale == 'en' and page.lang == 'es' %}
{% assign locale_url = page.url | remove_first: 'es/' %}
{% elsif locale == 'en' and page.lang == 'fr' %}
{% assign locale_url = page.url | remove_first: 'fr/' %}
{% elsif locale == page.lang %}
{% assign locale_url = page.url %}
{% else %}
{% assign locale_url = page.url | replace_first: page.lang, locale %}
{% endif %}
{% endif %}
<a href="{{ locale_url | prepend: site.baseurl }}" lang="{{ locale }}">
<a href="{{ page.url | delocalize_url | locale_url: locale }}" lang="{{ locale }}">
{{ site.data.[locale].settings.global.locales[locale] }}
</a>
</li>
Expand Down
17 changes: 13 additions & 4 deletions _plugins/locale_url_filter.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,23 @@ module Jekyll
module LocaleUrlFilter
LOCALE_STRING_CONSTANT = '__LOCALE_BASE_URL__'.freeze

def locale_url(path = '')
def locale_url(path = '', locale = nil)
site_base_url = @context.registers[:site].baseurl
locale_prefix = @context.registers[:page]['base_path']
site_base_url.to_s + locale_prefix.to_s + path
locale ||= @context.registers[:page]['lang']
permalink = @context.registers[:site].collections[locale].metadata['permalink']
site_base_url.to_s + Jekyll::URL.new(
template: permalink,
placeholders: { collection: locale, path: path },
).to_s
end

def delocalize_url(path, locale = nil)
locale ||= @context.registers[:page]['lang']
path.gsub(%r{^/#{locale}/}, '/')
end

def replace_locale_base_url(input)
input.gsub LOCALE_STRING_CONSTANT, locale_url
input.gsub(LOCALE_STRING_CONSTANT, locale_url.chomp('/'))
end
end
end
Expand Down
278 changes: 278 additions & 0 deletions spec/_plugins/locale_url_filter_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,278 @@
require 'jekyll'
require './_plugins/locale_url_filter'

class JekyllFilter
include Jekyll::LocaleUrlFilter

def initialize(config, page_data)
@site = Jekyll::Site.new(Jekyll::Configuration.from(config))
page = Jekyll::Page.new(@site, @site.source, '', 'README.md')
page.data.merge!(page_data)
@context = Liquid::Context.new(@site.site_payload, {}, site: @site, page: page)
end
end

RSpec.describe Jekyll::LocaleUrlFilter do
let(:config) { {} }
let(:page_data) { { 'lang' => 'en' } }
let(:instance) { JekyllFilter.new(config, page_data) }

describe '#locale_url' do
let(:path) { '' }
let(:locale) { nil }
subject(:locale_url) { instance.locale_url(path, locale) }

context 'without site base url' do
let(:config) do
{
'collections' => {
'en' => { 'permalink' => '/:path/' },
'es' => { 'permalink' => '/:path/' },
},
}
end

context 'without path' do
context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('/')
end
end
end

context 'with path' do
let(:path) { '/path/' }

context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('/path/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('/path/')
end
end
end
end

context 'with collection in permalink' do
let(:config) do
{
'collections' => {
'en' => { 'permalink' => '/:collection/:path/' },
'es' => { 'permalink' => '/:collection/:path/' },
},
}
end

context 'without path' do
context 'without locale' do
it 'renders with locale from page data' do
expect(locale_url).to eq('/en/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders with locale' do
expect(locale_url).to eq('/es/')
end
end
end

context 'with path' do
let(:path) { '/path/' }

context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('/en/path/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('/es/path/')
end
end
end
end

context 'with site base url' do
context 'without collection in permalink' do
let(:config) do
{
'baseurl' => 'https://example.com',
'collections' => {
'en' => { 'permalink' => '/:path/' },
'es' => { 'permalink' => '/:path/' },
},
}
end

context 'without path' do
context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('https://example.com/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('https://example.com/')
end
end
end

context 'with path' do
let(:path) { '/path/' }

context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('https://example.com/path/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('https://example.com/path/')
end
end
end
end

context 'with collection in permalink' do
let(:config) do
{
'baseurl' => 'https://example.com',
'collections' => {
'en' => { 'permalink' => '/:collection/:path/' },
'es' => { 'permalink' => '/:collection/:path/' },
},
}
end

context 'without path' do
context 'without locale' do
it 'renders with locale from page data' do
expect(locale_url).to eq('https://example.com/en/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders with locale' do
expect(locale_url).to eq('https://example.com/es/')
end
end
end

context 'with path' do
let(:path) { '/path/' }

context 'without locale' do
it 'renders without locale' do
expect(locale_url).to eq('https://example.com/en/path/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'renders without locale' do
expect(locale_url).to eq('https://example.com/es/path/')
end
end
end
end
end
end

describe '#delocalize_url' do
let(:path) { '' }
let(:locale) { nil }
let(:page_data) { { 'lang' => 'es' } }
subject(:delocalized_url) { instance.delocalize_url(path, locale) }

context 'path not including locale' do
let(:path) { '/fr/example/' }

context 'without locale' do
it 'uses page data and does not modify path' do
expect(delocalized_url).to eq(path)
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'does not modify path' do
expect(delocalized_url).to eq(path)
end
end
end

context 'path including locale' do
let(:path) { '/es/example/' }

context 'without locale' do
it 'uses page data and delocalizes url' do
expect(delocalized_url).to eq('/example/')
end
end

context 'with locale' do
let(:locale) { 'es' }

it 'delocalizes url' do
expect(delocalized_url).to eq('/example/')
end
end
end
end

describe '#replace_locale_base_url' do
let(:input) { "#{Jekyll::LocaleUrlFilter::LOCALE_STRING_CONSTANT}/help/" }
subject(:locale_url) { instance.replace_locale_base_url(input) }

context 'without site base url' do
let(:config) { { 'collections' => { 'en' => { 'permalink' => '/:path/' } } } }

it 'replaces using page data' do
expect(locale_url).to eq('/help/')
end
end

context 'with site base url' do
let(:config) do
{
'baseurl' => 'https://example.com',
'collections' => { 'en' => { 'permalink' => '/:path/' } },
}
end

it 'replaces using page data' do
expect(locale_url).to eq('https://example.com/help/')
end
end
end
end