feat: multi language support (#254)

* feat: multitranslational support

* - completion of settings page
- completion of sidebar

* sidebar rerendering bug fix

* completion of the lesson navigation & materials page

* completion of the course navigation

* completion of requested languages

* - Implementation of Language Picker
- Rename Bug Fixes

* checkpoint save

* - addition of the language picker to the onboarding.
- addition of the language switcher for the lesson notes.

* merge completion

* initialization of the new branch

* add transition.svelte file

* lesson note bug fix

* feat: add translation migration

* completion of translation

* fix height issue of dropdown

* refactoring

* fix: improve code with LOCALE from db

* finally get it fully functional

* connect with AI

* backward compatibility for lesson note

* preserve old content, when generating AI content

* undo translations in upgrade modal

* fix duplicate key issue from codacy trigger

---------

Co-authored-by: Rotimi Best <[email protected]>
This commit is contained in:
Adeyemi Adetunji
2024-04-19 05:45:48 +01:00
committed by GitHub
co-authored by Rotimi Best
parent ff7d2cee35
commit d75e2f258e
153 changed files with 11264 additions and 1130 deletions
@@ -2,6 +2,7 @@
import { goto } from '$app/navigation';
import Community from '$lib/components/Org/Community/index.svelte';
import PrimaryButton from '$lib/components/PrimaryButton/index.svelte';
import { t } from '$lib/utils/functions/translations';
function askCommunity() {
goto(`/lms/community/ask`);
@@ -15,8 +16,8 @@
<section class="w-full max-w-4xl mx-auto">
<div class="py-10 px-5">
<div class="flex items-center justify-between mb-10">
<h1 class="dark:text-white text-3xl font-bold">Community</h1>
<PrimaryButton label="Ask Community" onClick={askCommunity} />
<h1 class="dark:text-white text-3xl font-bold">{$t('community.title')}</h1>
<PrimaryButton label={$t('community.ask_button')} onClick={askCommunity} />
</div>
<Community isLMS={true} />
@@ -178,11 +178,11 @@
if (error) {
console.error('Error: commenting', error);
snackbar.error('Error - Please try again later');
snackbar.error('snackbar.community.error.try_again');
} else {
console.log('Success: commenting', data);
snackbar.success('Comment Submitted!');
snackbar.success('snackbar.community.success.comment_submitted');
// Add to comment
const _c = data?.[0];
@@ -230,7 +230,7 @@
const { error } = await supabase.from(table).update({ votes }).match({ id: matchId });
if (error) {
console.error('Error: upvoteQuestion', error);
snackbar.error('Error - Please try again later');
snackbar.error('snackbar.community.error.try_again');
} else {
if (isQuestion) {
voted.question = true;
@@ -263,13 +263,14 @@
const { error } = await supabase
.from('community_question')
.update({
...editContent,
title: editContent.title,
body: editContent.body,
course_id: editContent.courseId
})
.match({ id: question.id });
if (error) {
console.error('Error: handleQuestionEdit', error);
snackbar.error('Error - Please try again later');
snackbar.error('snackbar.community.error.try_again');
} else {
question.title = editContent.title;
question.body = editContent.body;
@@ -298,11 +299,11 @@
deleteComment.isDeleting = false;
if (error) {
snackbar.error('Error deleting comments');
snackbar.error('snackbar.community.error.deleting_comments');
console.log('Error deleting comments', error);
return;
}
snackbar.success('Deleted successfully');
snackbar.success('snackbar.community.success.success_delete');
question.comments = question.comments.filter((c) => c.id !== deleteComment.commentId);
deleteComment.shouldDelete = false;
@@ -319,7 +320,7 @@
.match({ question_id: deleteQuestion.questionId });
if (commentDeleteError) {
snackbar.error('Error deleting comments');
snackbar.error('snackbar.community.error.deleting_comments');
console.log('Error deleting comments', commentDeleteError);
deleteQuestion.isDeleting = false;
@@ -332,12 +333,12 @@
.match({ id: deleteQuestion.questionId });
if (questionDeleteError) {
snackbar.error('Error deleting question');
snackbar.error('snackbar.community.error.deleting_question');
console.log('Error deleting question', questionDeleteError);
return;
}
snackbar.success('Deleted successfully');
snackbar.success('snackbar.community.success.success_delete');
goto(`/lms/community`);
deleteQuestion.isDeleting = false;
}
@@ -394,7 +395,7 @@
errorMessage={errors.title}
/>
<Dropdown
class="w-[25%] h-fit"
class="w-[25%] h-full"
size="xl"
label="Select Course"
items={fetchedCourses.map((course) => ({ id: course.id, text: course.title }))}
@@ -12,6 +12,7 @@
import TextField from '$lib/components/Form/TextField.svelte';
import { profile } from '$lib/utils/store/user';
import { fetchCourses } from '$lib/components/Courses/api';
import { t } from '$lib/utils/functions/translations';
let errors: {
title?: string;
@@ -57,7 +58,7 @@
} else {
const slug = question[0]?.slug;
console.log('Success: asking question in lms', question, slug);
snackbar.success('Question Submitted!');
snackbar.success('snackbar.community.success.question_submitted');
goto(`/lms/community/${slug}`);
}
@@ -77,25 +78,26 @@
<section class="w-full max-w-3xl mx-auto">
<div class="p-5">
<a class="text-gray-500 dark:text-white text-md flex items-center" href={`/lms/community`}>
<ArrowLeftIcon size={24} class="carbon-icon dark:text-white" /> Go Back
<ArrowLeftIcon size={24} class="carbon-icon dark:text-white" />
{$t('community.ask.go_back')}
</a>
<div class="flex items-center justify-between">
<h1 class="dark:text-white text-3xl font-bold">Ask the community</h1>
<PrimaryButton label="Publish" onClick={handleSave} />
<h1 class="dark:text-white text-3xl font-bold">{$t('community.ask.ask_the')}</h1>
<PrimaryButton label={$t('community.ask.publish')} onClick={handleSave} />
</div>
</div>
<div class="mb-3 p-2 flex gap-x-5 justify-between">
<TextField
bind:value={fields.title}
placeholder="Title"
placeholder={$t('community.ask.title')}
errorMessage={errors.title}
className="w-[75%]"
/>
<Dropdown
class="w-[25%]"
class="w-[25%] h-full"
size="xl"
label="Select Course"
label={$t('community.ask.select_course')}
invalid={!!errors.courseId}
invalidText={errors.courseId}
items={fetchedCourses.map((course) => ({ id: course.id, text: course.title }))}
@@ -105,7 +107,7 @@
<TextEditor
bind:value={fields.body}
placeholder="Ask the community any question you might have"
placeholder={$t('community.ask.ask_community')}
onChange={(html) => (fields.body = html)}
/>
</section>