feat(bisaya-course): add didactics fragments for "Haus & Familie" lessons
All checks were successful
Deploy to production / deploy (push) Successful in 2m56s

- Introduced comprehensive didactics snippets for the "Haus & Familie" lesson, including learning goals, core patterns, grammar focus, speaking prompts, and practical tasks.
- Updated the lesson retrieval logic to incorporate these new fragments as a fallback for core patterns, enhancing the robustness of lesson content delivery.
- Modified the vocab service to utilize the new didactics fragments, ensuring a seamless integration into the existing lesson structure.
This commit is contained in:
Torsten Schulz (local)
2026-04-16 22:44:57 +02:00
parent 229bdc96bf
commit 712370cad3
3 changed files with 79 additions and 4 deletions

View File

@@ -22,3 +22,63 @@ export const BISAYA_PHASE1_DIDACTICS = {
]
}
};
/**
* Volle Didaktik-Snippets für Lektionen, die in update-bisaya-didactics.js gepflegt werden sollen
* und als API-Fallback dienen, wenn core_patterns in der DB fehlen (z. B. Kurz-Wiederholung).
*/
export const BISAYA_DIDACTICS_FRAGMENTS = {
'Haus & Familie': {
learningGoals: [
'Wichtige Wörter für Haus, Räume und Familie zuordnen und aussprechen.',
'Mit „Naa … sa …“ sagen, wo sich jemand oder etwas im Haus befindet.',
'Kurze Sätze über Zuhause und Familie verstehen und nachsprechen.'
],
corePatterns: [
{ target: 'Balay', gloss: 'Haus' },
{ target: 'Kwarto', gloss: 'Zimmer' },
{ target: 'Kusina', gloss: 'Küche' },
{ target: 'Sala', gloss: 'Wohnzimmer' },
{ target: 'Banyo', gloss: 'Badezimmer' },
{ target: 'Pultahan', gloss: 'Tür' },
{ target: 'Bintana', gloss: 'Fenster' },
{ target: 'Atop', gloss: 'Dach' },
{ target: 'Pamilya', gloss: 'Familie' },
{ target: 'Among pamilya', gloss: 'unsere Familie' },
{ target: 'Naa ko sa balay.', gloss: 'Ich bin zu Hause.' },
{ target: 'Naa sila sa kusina.', gloss: 'Sie sind in der Küche.' },
{ target: 'Asa ang kusina?', gloss: 'Wo ist die Küche?' },
{ target: 'Ang among balay.', gloss: 'Unser Haus.' }
],
grammarFocus: [
{
title: 'Naa … sa … für Ort',
text: '„Naa“ drückt aus, dass jemand oder etwas irgendwo ist; „sa“ verbindet mit dem Ort.',
example: 'Naa ko sa balay. Naa sila sa kusina.'
},
{
title: 'among = unser (Plural inklusiv)',
text: '„Among“ passt zu „wir/unsere“ im Sinne von Familie oder Gruppe.',
example: 'Among pamilya. Ang among balay.'
}
],
speakingPrompts: [
{
title: 'Räume benennen',
prompt: 'Nenne Küche, Wohnzimmer und Badezimmer auf Bisaya.',
cue: 'Kusina, sala, banyo.'
},
{
title: 'Wer ist wo?',
prompt: 'Sage, dass du zu Hause bist, und frage, wo die Küche ist.',
cue: 'Naa ko sa balay. Asa ang kusina?'
}
],
practicalTasks: [
{
title: 'Rundgang',
text: 'Geh in Gedanken durch dein Zuhause und benenne jeden Raum laut auf Bisaya.'
}
]
}
};

View File

@@ -9,6 +9,7 @@
import { sequelize } from '../utils/sequelize.js';
import VocabCourseLesson from '../models/community/vocab_course_lesson.js';
import { getBisayaLessonPedagogy } from './bisaya-course-phase2-pedagogy.js';
import { BISAYA_DIDACTICS_FRAGMENTS } from './bisaya-course-phase1.js';
/** Alte Kurstitel → aktueller Schlüssel in LESSON_DIDACTICS (bestehende Datenbanken). */
export const LEGACY_DIDACTICS_TITLE_MAP = {
@@ -140,6 +141,7 @@ export const LESSON_DIDACTICS = {
{ title: 'Gesprächspraxis', text: 'Spiele einen kurzen Familienaustausch mit Frage, Antwort und Fürsorge nach.' }
]
},
'Haus & Familie': BISAYA_DIDACTICS_FRAGMENTS['Haus & Familie'],
'Gefühle & Zuneigung': {
learningGoals: [
'Wichtige Gefühle und Zuneigungsformeln sicher unterscheiden.',

View File

@@ -12,7 +12,7 @@ import UserParam from '../models/community/user_param.js';
import { sequelize } from '../utils/sequelize.js';
import { notifyUser } from '../utils/socket.js';
import { Op } from 'sequelize';
import { BISAYA_PHASE1_DIDACTICS } from '../scripts/bisaya-course-phase1.js';
import { BISAYA_PHASE1_DIDACTICS, BISAYA_DIDACTICS_FRAGMENTS } from '../scripts/bisaya-course-phase1.js';
export default class VocabService {
_normalizeIsoDate(value) {
@@ -979,13 +979,26 @@ export default class VocabService {
const learningGoals = this._normalizeStringList(plainLesson.learningGoals);
const extractedTrainerVocabs = this._extractTrainerVocabsFromExercises(grammarExercises);
const phase1FallbackCorePatterns = BISAYA_PHASE1_DIDACTICS[plainLesson.title]?.corePatterns || [];
const corePatterns = this._mergeCorePatternGlosses(
let resolvedCorePatterns = this._mergeCorePatternGlosses(
this._enrichCorePatternsWithGloss(
this._normalizeCorePatternList(plainLesson.corePatterns),
extractedTrainerVocabs
),
phase1FallbackCorePatterns
);
if (
!resolvedCorePatterns.length
&& BISAYA_DIDACTICS_FRAGMENTS[plainLesson.title]?.corePatterns?.length
) {
const frag = BISAYA_DIDACTICS_FRAGMENTS[plainLesson.title];
resolvedCorePatterns = this._mergeCorePatternGlosses(
this._enrichCorePatternsWithGloss(
this._normalizeCorePatternList(frag.corePatterns),
extractedTrainerVocabs
),
phase1FallbackCorePatterns
);
}
const grammarFocus = this._normalizeStructuredList(plainLesson.grammarFocus, ['title', 'text', 'example']);
const explicitSpeakingPrompts = this._normalizeStructuredList(plainLesson.speakingPrompts, ['title', 'prompt', 'cue']);
const practicalTasks = this._normalizeStructuredList(plainLesson.practicalTasks, ['title', 'text']);
@@ -998,8 +1011,8 @@ export default class VocabService {
'Ein bis zwei Satzmuster aktiv anwenden.',
'Kurze Sätze oder Mini-Dialoge zum Thema selbst bilden.'
],
corePatterns: corePatterns.length > 0
? corePatterns
corePatterns: resolvedCorePatterns.length > 0
? resolvedCorePatterns
: this._mergeCorePatternGlosses(
this._enrichCorePatternsWithGloss(
uniquePatterns.slice(0, 5).map((s) => ({ target: String(s || '').trim(), gloss: '' })).filter((p) => p.target),