Skip to content

Commit 19c56cc

Browse files
authored
Set up internationalization of vue components (#1360)
* Set up internationalization * Update tests to work with internationalization plugin
1 parent 03edc51 commit 19c56cc

24 files changed

+724
-43
lines changed

Diff for: static/js/vue-cdr-access/package-lock.json

+551-3
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Diff for: static/js/vue-cdr-access/package.json

+2
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,11 @@
1919
"lodash.range": "^3.2.0",
2020
"lodash.sortby": "^4.7.0",
2121
"vue": "^3.2.28",
22+
"vue-i18n": "^9.1.9",
2223
"vue-router": "^4.0.12"
2324
},
2425
"devDependencies": {
26+
"@intlify/vue-i18n-loader": "^4.1.0",
2527
"@testing-library/jest-dom": "^5.16.1",
2628
"@vue/cli-plugin-babel": "^4.5.15",
2729
"@vue/cli-plugin-unit-jest": "^4.5.15",

Diff for: static/js/vue-cdr-access/src/components/browseSearch.vue

+2-2
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,10 @@
66
:placeholder="searchText" :aria-label="searchText">
77
</div>
88
<div class="control">
9-
<button @click="getResults" class="button">Search</button>
9+
<button @click="getResults" class="button">{{ $t('search.search') }}</button>
1010
</div>
1111
</div>
12-
<a class="clear-results" href="#" @click.prevent="clearSearch">Clear search results</a>
12+
<a class="clear-results" href="#" @click.prevent="clearSearch">{{ $t('search.clear_search') }}</a>
1313
</div>
1414
</template>
1515

Diff for: static/js/vue-cdr-access/src/components/browseSort.vue

+5-5
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
<template>
22
<div class="browse-sort select is-medium">
33
<select @change="sortRecords" v-model="sort_order" aria-label="Sort options">
4-
<option value="default,normal">Sort by Relevance</option>
5-
<option value="title,normal">Title A-Z</option>
6-
<option value="title,reverse">Title Z-A</option>
7-
<option value="dateAdded,normal">Date Created (newest)</option>
8-
<option value="dateAdded,reverse">Date Created (oldest)</option>
4+
<option value="default,normal">{{ $t('sort.relevance') }}</option>
5+
<option value="title,normal">{{ $t('sort.title_a-z') }}</option>
6+
<option value="title,reverse">{{ $t('sort.title_z-a') }}</option>
7+
<option value="dateAdded,normal">{{ $t('sort.date_created_newest') }}</option>
8+
<option value="dateAdded,reverse">{{ $t('sort.date_created_oldest') }}</option>
99
</select>
1010
</div>
1111
</template>

Diff for: static/js/vue-cdr-access/src/components/displayWrapper.vue

+1-1
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@
1818
<browse-display v-if="isBrowseDisplay" :record-list="record_list"></browse-display>
1919
<list-display v-else :record-list="record_list" :is-record-browse="true"></list-display>
2020
</div>
21-
<p v-else class="spacing">No records were found.</p>
21+
<p v-else class="spacing">{{ $t('search.no_results') }}</p>
2222
<modal-metadata :uuid="uuid" :title="container_name"></modal-metadata>
2323
<pagination browse-type="display" :number-of-records="record_count"></pagination>
2424
</div>

Diff for: static/js/vue-cdr-access/src/components/facets.vue

+2-2
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33
<a v-if="selected_facets.length > 0" id="clear-all" class="button is-link is-small" @click.prevent="clearAll()">
44
<span class="icon is-small">
55
<i class="fas fa-times"></i>
6-
</span> Clear filters</a>
7-
<h2 class="facet-header">Filter results by...</h2>
6+
</span> {{ $t('facets.clear')}}</a>
7+
<h2 class="facet-header">{{ $t('facets.filter') }}</h2>
88
<div class="facet-display" v-for="facet in this.sortedFacetsList">
99
<div v-if="showFacetDisplay(facet)">
1010
<h3>{{ facetName(facet.name) }}</h3>

Diff for: static/js/vue-cdr-access/src/components/listDisplay.vue

+4-4
Original file line numberDiff line numberDiff line change
@@ -32,14 +32,14 @@
3232
<a :class="{deleted: markedForDeletion(record)}" :href="recordUrl(record.id, linkBrowseType)">{{ record.title }}</a>
3333
<span v-if="record.type !== 'File'" class="item_container_count">{{ countDisplay(record.counts.child) }}</span>
3434
</div>
35-
<div><span class="has-text-weight-bold">Date Deposited:</span> {{ formatDate(record.added) }}</div>
35+
<div><span class="has-text-weight-bold">{{ $t('display.date_deposited') }}:</span> {{ formatDate(record.added) }}</div>
3636
<div v-if="record.objectPath.length >= 3 && record.type !== 'Collection'">
37-
<span class="has-text-weight-bold">Collection:</span> <a class="metadata-link" :href="recordUrl(record.objectPath[2].pid, linkBrowseType)">{{ collectionInfo(record.objectPath) }}</a>
37+
<span class="has-text-weight-bold">{{ $t('display.collection') }}:</span> <a class="metadata-link" :href="recordUrl(record.objectPath[2].pid, linkBrowseType)">{{ collectionInfo(record.objectPath) }}</a>
3838
</div>
3939
<div v-if="record.objectPath.length >= 3 && showCollection(record)">
40-
<p class="collection_id"><span class="has-text-weight-bold">Collection Number:</span> {{ record.objectPath[2].collectionId }}</p>
40+
<p class="collection_id"><span class="has-text-weight-bold">{{ $t('display.collection_number') }}:</span> {{ record.objectPath[2].collectionId }}</p>
4141
</div>
42-
<div v-if="record.type === 'Work' || record.type === 'File'"><span class="has-text-weight-bold">File Type:</span> {{ getFileType(record.datastream) }}</div>
42+
<div v-if="record.type === 'Work' || record.type === 'File'"><span class="has-text-weight-bold">{{ $t('display.file_type') }}:</span> {{ getFileType(record.datastream) }}</div>
4343
</div>
4444
</li>
4545
</ul>

Diff for: static/js/vue-cdr-access/src/components/modalMetadata.vue

+1-1
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
<slot name="header">
1111
<div class="column is-12">
1212
<h3>{{ title }}</h3>
13-
<button class="button is-small" @click="showModal = false">Close</button>
13+
<button class="button is-small" @click="showModal = false">{{ $t('modal.close') }}</button>
1414
</div>
1515
</slot>
1616
</div>

Diff for: static/js/vue-cdr-access/src/components/pagination.vue

+2-2
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
<div class="columns pagination is-mobile">
33
<div class="column is-12">
44
<ul v-if="numberOfRecords > 0">
5-
<li v-if="currentPage !== 1"><a class="back-next start" @click.prevent="pageUrl(currentPage - 1)" href="#">Previous</a></li>
5+
<li v-if="currentPage !== 1"><a class="back-next start" @click.prevent="pageUrl(currentPage - 1)" href="#">{{ $t('pagination.previous') }}</a></li>
66
<li v-else class="no-link start">Previous</li>
77
<li id="first-page-link" v-if="currentPage >= pageLimit - 1 && totalPageCount > pageLimit"><a @click.prevent="pageUrl(1)" href="#" class="page-number"
88
:class="{ current: currentPage === 1 }">1</a> ...</li>
@@ -13,7 +13,7 @@
1313
... <a @click.prevent="pageUrl(totalPageCount)" href="#" class="page-number"
1414
:class="{ current: currentPage === totalPageCount }">{{totalPageCount }}</a>
1515
</li>
16-
<li v-if="currentPage < totalPageCount"><a class="back-next end" @click.prevent="pageUrl(currentPage + 1)" href="#">Next</a></li>
16+
<li v-if="currentPage < totalPageCount"><a class="back-next end" @click.prevent="pageUrl(currentPage + 1)" href="#">{{ $t('pagination.next') }}</a></li>
1717
<li v-else class="no-link end">Next</li>
1818
</ul>
1919
</div>

Diff for: static/js/vue-cdr-access/src/components/searchWrapper.vue

+1-1
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
</div>
2222
<list-display v-if="records.length > 0" :record-list="records" :use-saved-browse-type="true"></list-display>
2323
</div>
24-
<p v-else class="spacing" :class="facetsWithNoResults">No records were found.</p>
24+
<p v-else class="spacing" :class="facetsWithNoResults">{{ $t('search.no_results') }}</p>
2525
</div>
2626

2727
<div class="columns is-mobile">

Diff for: static/js/vue-cdr-access/src/components/viewType.vue

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
<template>
22
<div id="browse-display-type" class="display-wrapper">
33
<div id="browse-btns" @click="setMode">
4-
<i id="list-display" title="List View" class="fas fa-th-list" :class="{'is-selected': !isGallery}"></i>
5-
<i id="gallery-display" title="Gallery View" class="fas fa-th" :class="{'is-selected': isGallery}"></i>
4+
<i id="list-display" :title="$t('view.list')" class="fas fa-th-list" :class="{'is-selected': !isGallery}"></i>
5+
<i id="gallery-display" :title="$t('view.gallery')" class="fas fa-th" :class="{'is-selected': isGallery}"></i>
66
</div>
77
</div>
88
</template>

Diff for: static/js/vue-cdr-access/src/components/worksOnly.vue

+2-2
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,12 @@
22
<div id="browse-display-type" class="display-wrapper" v-if="!adminUnit">
33
<div class="field">
44
<input @click="showWorks" type="checkbox" id="works-only" class="is-checkradio is-large" v-model="works_only">
5-
<label for="works-only"><p>Show only works</p></label>
5+
<label for="works-only"><p>{{ $t('works_only.show')}}</p></label>
66
</div>
77
<div class="note">
88
<div class="display-note-btn">?
99
<div class="arrow"></div>
10-
<span class="browse-tip">Show all files without organizational folders.</span>
10+
<span class="browse-tip">{{ $t('works_only.show_tip') }}</span>
1111
</div>
1212
</div>
1313
</div>

Diff for: static/js/vue-cdr-access/src/main.js

+9-1
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,19 @@
11
import { createApp, h } from 'vue'
2+
import { createI18n } from 'vue-i18n'
23
import App from './App.vue'
34
import router from './router'
5+
import translations from '@/translations';
46

57
if (document.getElementById('app') !== null && window.dcr_browse_records === undefined) {
8+
const i18n = createI18n({
9+
locale: 'en',
10+
fallbackLocale: 'en',
11+
messages: translations
12+
});
13+
614
window.dcr_browse_records = createApp({
715
render() {
816
return h(App);
917
}
10-
}).use(router).mount('#app');
18+
}).use(router).use(i18n).mount('#app');
1119
}

Diff for: static/js/vue-cdr-access/src/translations.js

+41
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
export default {
2+
"en": {
3+
"display": {
4+
"collection": "Collection",
5+
"collection_number": "Collection Number",
6+
"date_deposited": "Date Deposited",
7+
"file_type": "File Type"
8+
},
9+
"facets": {
10+
"clear": "Clear filters",
11+
"filter": "Filter results by..."
12+
},
13+
"modal": {
14+
"close": "Close"
15+
},
16+
"pagination": {
17+
"next": "Next",
18+
"previous": "Previous"
19+
},
20+
"search": {
21+
"clear_search": "Clear search results",
22+
"no_results": "No records were found.",
23+
"search": "Search"
24+
},
25+
"sort": {
26+
"relevance": "Sort by Relevance",
27+
"title_a-z": "Title A-Z",
28+
"title_z-a": "Title Z-A",
29+
"date_created_newest": "Date Created (newest)",
30+
"date_created_oldest": "Date Created (oldest)"
31+
},
32+
"view": {
33+
"gallery": "Gallery View",
34+
"list": "List View"
35+
},
36+
"works_only": {
37+
"show": "Show only works",
38+
"show_tip": "Show all files without organizational folders."
39+
}
40+
}
41+
}

Diff for: static/js/vue-cdr-access/tests/unit/browseSearch.spec.js

+13-3
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,20 @@
11
import { shallowMount, flushPromises } from '@vue/test-utils';
2+
import { createI18n } from 'vue-i18n';
23
import { createRouter, createWebHistory } from 'vue-router';
34
import browseSearch from '@/components/browseSearch.vue';
45
import displayWrapper from "@/components/displayWrapper";
6+
import translations from "@/translations";
57

68
const query = 'Test Collection';
79
let wrapper, router;
810

911
describe('browseSearch.vue', () => {
12+
const i18n = createI18n({
13+
locale: 'en',
14+
fallbackLocale: 'en',
15+
messages: translations
16+
});
17+
1018
beforeEach(async () => {
1119
router = createRouter({
1220
history: createWebHistory(process.env.BASE_URL),
@@ -20,7 +28,7 @@ describe('browseSearch.vue', () => {
2028
});
2129
wrapper = shallowMount(browseSearch, {
2230
global: {
23-
plugins: [router]
31+
plugins: [i18n, router]
2432
},
2533
props: {
2634
objectType: 'Folder'
@@ -69,7 +77,8 @@ describe('browseSearch.vue', () => {
6977
global: {
7078
mocks: {
7179
$route
72-
}
80+
},
81+
plugins: [i18n]
7382
}
7483
});
7584
expect(wrapper.find('input').attributes('placeholder')).toBe('Search within this object');
@@ -86,7 +95,8 @@ describe('browseSearch.vue', () => {
8695
global: {
8796
mocks: {
8897
$route
89-
}
98+
},
99+
plugins: [i18n]
90100
},
91101
props: {
92102
objectType: 'Folder'

Diff for: static/js/vue-cdr-access/tests/unit/browseSort.spec.js

+10-2
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,18 @@ import { createRouter, createWebHistory } from 'vue-router';
33
import browseSort from '@/components/browseSort.vue';
44
import displayWrapper from '@/components/displayWrapper';
55
import searchWrapper from '@/components/searchWrapper';
6+
import {createI18n} from "vue-i18n";
7+
import translations from "@/translations";
68

79
let wrapper, wrapper_search, router;
810

911
describe('browseSort.vue', () => {
12+
const i18n = createI18n({
13+
locale: 'en',
14+
fallbackLocale: 'en',
15+
messages: translations
16+
});
17+
1018
beforeEach(() => {
1119
router = createRouter({
1220
history: createWebHistory(process.env.BASE_URL),
@@ -25,7 +33,7 @@ describe('browseSort.vue', () => {
2533
});
2634
wrapper = mount(browseSort, {
2735
global: {
28-
plugins: [router]
36+
plugins: [router, i18n]
2937
},
3038
props: {
3139
browseType: 'display'
@@ -34,7 +42,7 @@ describe('browseSort.vue', () => {
3442

3543
wrapper_search = mount(browseSort, {
3644
global: {
37-
plugins: [router]
45+
plugins: [router, i18n]
3846
},
3947
props: {
4048
browseType: 'search'

Diff for: static/js/vue-cdr-access/tests/unit/displayWrapper.spec.js

+9-1
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ import { shallowMount, flushPromises } from '@vue/test-utils'
22
import { createRouter, createWebHistory } from 'vue-router';
33
import displayWrapper from '@/components/displayWrapper.vue';
44
import moxios from "moxios";
5+
import {createI18n} from "vue-i18n";
6+
import translations from "@/translations";
57

68
let wrapper, router;
79
const record_list = [
@@ -43,6 +45,12 @@ const response = {
4345
};
4446

4547
describe('displayWrapper.vue', () => {
48+
const i18n = createI18n({
49+
locale: 'en',
50+
fallbackLocale: 'en',
51+
messages: translations
52+
});
53+
4654
beforeEach(() => {
4755
moxios.install();
4856

@@ -59,7 +67,7 @@ describe('displayWrapper.vue', () => {
5967

6068
wrapper = shallowMount(displayWrapper, {
6169
global: {
62-
plugins: [router]
70+
plugins: [router, i18n]
6371
},
6472
data() {
6573
return {

Diff for: static/js/vue-cdr-access/tests/unit/facets.spec.js

+10-2
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,19 @@ import { createRouter, createWebHistory } from 'vue-router';
33
import facets from '@/components/facets.vue';
44
import searchWrapper from '@/components/searchWrapper.vue'
55
import displayWrapper from '@/components/displayWrapper';
6+
import {createI18n} from "vue-i18n";
7+
import translations from "@/translations";
68

79

810
let router, wrapper, collection, selected_facet, selected_sub_facet;
911

1012
describe('facets.vue', () => {
13+
const i18n = createI18n({
14+
locale: 'en',
15+
fallbackLocale: 'en',
16+
messages: translations
17+
});
18+
1119
beforeEach(() => {
1220
router = createRouter({
1321
history: createWebHistory(process.env.BASE_URL),
@@ -27,7 +35,7 @@ describe('facets.vue', () => {
2735

2836
wrapper = shallowMount(facets, {
2937
global: {
30-
plugins: [router]
38+
plugins: [router, i18n]
3139
},
3240
props: {
3341
facetList: [
@@ -109,7 +117,7 @@ describe('facets.vue', () => {
109117
it("does not display facets with no returned results", () => {
110118
let emptyFacetWrapper = shallowMount(facets, {
111119
global: {
112-
plugins: [router]
120+
plugins: [router, i18n]
113121
},
114122
props: {
115123
facetList: [

0 commit comments

Comments
 (0)