Modifier le texte original
Permettre de modifier le texte original après que des traductions aient été ajoutées.
Plusieurs scénarios ont été identifiés :
- Modification à l'intérieur d'un bloc existant => Fonctionnel actuellement
- Ajout de plusieurs blocs à la fin d'un texte => Scénario 1
- Ajout de plusieurs blocs entre des blocs existants => Scénario 2
Voir si le Scénario 2 correspond réellement au besoin du client
Première ébauche du Scénario 1
M. Paul souhaite ajouter du texte à la fin de l'oeuvre originale initialement renseignée après que des traductions aient été ajoutées
Pré-requis
L'oeuvre X dispose de traductions
Déroulement
M. Paul sélectionne l’œuvre dont il dispose dans la liste des œuvres. Il accède ainsi à la page de visualisation de l’œuvre et ses traductions. M. Paul accède à l'édition depuis le bouton "Editer" M. Paul clique sur '+' située sous le l'oeuvre afin de faire apparaître un bloc vide M. Paul renseigne le texte pour ce bloc et peut ainsi ajouter du texte à la fin de l'oeuvre qui pourra être traduit par les utilisateurs
Première ébauche du Scénario 2
M. Paul souhaite ajouter du texte au sein de l'oeuvre originale initialement renseignée après que des traductions aient été ajoutées
Pré-requis
L'oeuvre X dispose de traductions
Déroulement
M. Paul sélectionne l’œuvre dont il dispose dans la liste des œuvres. Il accède ainsi à la page de visualisation de l’œuvre et ses traductions. M. Paul accède à l'édition depuis le bouton "Editer" M. Paul clique sur '+' située entre deux blocs de texte afin de faire apparaître un bloc vide M. Paul renseigne le texte pour ce bloc et peut ainsi ajouter du texte là où il le souhaite au sein de l'oeuvre qui pourra être traduit par les utilisateurs
À la suite des ébauches écrites, nous avons repris et modifié le scénario 1 à l'aide d'un exemple plus concret. Celui-ci correspond plus aux attentes évoquées par le client lors de la première réunion. Nous n'avons pas trouvé de différences notables entre le premier et le second scénario si ce n'est qu'il n'a pas été évoqué par le client et qu'il est probablement plus difficile techniquement.
Scénario 1
M. Paul, enseignant traducteur, a pour habitude de présenter des œuvres à ses élèves afin qu'ils s'exercent à la traduction. Le travail étant conséquent, il leur propose de les traduire chapitre par chapitre. Il leur a demandé la semaine passée de traduire le premier chapitre du célèbre roman X et désire maintenant leur proposer la suite.
Pré-requis
Le premier chapitre de l'oeuvre X a déjà été traduite.
Déroulement
M. Paul sélectionne X dans la liste des œuvres. Il accède ainsi à la page de visualisation de l’œuvre et ses traductions. Il clique ensuite sur le bouton "Editer" afin de compléter ce texte. Une fois l'édition active, M. Paul clique sur le bouton '+' situé sous le l'oeuvre ce qui fait apparaître un bloc vide qu'il complète avec le titre du second chapitre. Il lui suffit alors de continuer à publier le texte original en ajoutant le nombre de blocs nécessaires à l'écriture du second chapitre. Une fois sa tâche terminée il repasse en mode lecture à l'aide du bouton "Lire".
Bilan
M. Paul ayant réussi à ajouter le second chapitre, il peut alors demander à ses étudiants de continuer leur travail sur la traduction du roman X.
Travail effectué le lundi 30 mars
Le scénario 1 nous semble clair et explicite. Le scénario 2 a été abandonné. Nous faisons passer le ticket en maquette.
Maquette scénario 1
M. Paul accède à l'édition depuis le bouton "Editer" :

M. Paul clique sur '+' située sous le l'oeuvre afin de faire apparaître un bloc vide :

M. Paul renseigne le texte pour ce bloc et peut ainsi ajouter du texte à la fin de l'oeuvre qui pourra être traduit par les utilisateurs
@adeprez ; Maquette validé. Le ticket passe en test de recette.
Le client n'ayant pas explicité dans quel cadre il souhaite pouvoir éditer une oeuvre, il semble intéressant de le compléter avec le scénario 2.
En effet, par simple drag'n'drop il serait possible de déplacer ce nouveau champ à l'endroit souhaité. L'ajout d'un nouveau champ sur l'oeuvre originale entraine la création d'un nouveau champ au même endroit pour toutes les traductions déjà présentes.
Nouveau scénario
- M. Paul sélectionne l’œuvre dont il dispose dans la liste des œuvres, accédant ainsi à la page de visualisation de l’œuvre et ses traductions.
- M. Paul accède à l'édition depuis le bouton
Editer. - M. Paul clique sur le bouton
+situé sous le l'oeuvre afin de faire apparaître un bloc vide. - M. Paul peut déplacer ce bloc à l'endroit souhaité.
- M. Paul renseigne ensuite le texte pour ce bloc, permettant aux utlisateurs de traduire ce nouveau bloc.
Maquettes associées
M. Paul accède à l'édition depuis le bouton Editer

M. Paul clique sur le bouton + situé sous le l'oeuvre afin de faire apparaître un bloc vide.

M. Paul peut déplacer ce bloc à l'endroit souhaité.

M. Paul renseigne ensuite le texte pour ce bloc, permettant aux utlisateurs de traduire ce nouveau bloc.
[Dev] Ajouter du texte bloc par bloc est fastidieux, il pourrait être pertinent de scinder automatiquement le bloc en plusieurs blocs en se basant sur les doubles retours chariot tel que défini dans l'ajout d'un texte original.
L'ajout d'un bloc et le découpage par double-retour chariot sont validés. L'ajout d'un bloc en sein du texte serait appréciée.
Le client a spécifié dans quel contexte il souhaite pouvoir insérer des 'blocs vides' au milieu d'un texte déjà traduit. Le client souhaite pouvoir scinder le contenu d'un bloc en allant à la ligne.
Modification du scénario 2
- M. Paul sélectionne dans la liste des œuvres une oeuvre qui dispose déjà de traduction. Il accède ainsi à la page de visualisation de l’œuvre et ses traductions.
- M. Paul accède à l'édition depuis le bouton Editer.
- M. Paul insère un double retour chariot au sein d'un bloc, à l'endroit où il souhaite scinder le bloc.
- M. Paul repasse en mode 'lecture' en cliquant sur le bouton "Lire".
- Le bloc initial a été scindé à l'endoit choisi et M. Paul peut désormais voir deux blocs différents.
- Les traductions ne seront pas scindées automatiquement.
- M. Paul devra faire les modifications manuellement afin que les traductions soient scindées.
Maquettes associées
M. Paul accède à l'édition depuis le bouton Editer
M. Paul insère un double retour chariot au sein d'un bloc, à l'endroit où il souhaite scinder le bloc.
Le bloc initial a été scindé à l'endoit choisi et M. Paul peut désormais voir deux blocs différents.
M. Paul devra faire les modifications manuellement afin que les traductions soient scindées.
Nous avons analysé les tests de recette existants sur cette fonctionnalité. Le test 'Create_translation.rb' a été testé en partie. Voici les modifications que nous lui avons déjà apportées :
feature 'Create a translation' do
background do
visit '/works/'
click_on 'Ajouter une oeuvre'
fill_in 'title', :with => 'The Raven'
fill_in 'work-creator', :with => 'Edgar Allan Poe'
find('input[type="submit"][name=""]').click
sleep 5
first('.edit').click
fill_in find('.fulltext'), :with => 'Once upon a midnight dreary, while I pondered, weak and weary, \n\n Over many a quaint and curious volume of forgotten lore'
click_on 'Save'
end
Le dernier fill_in ne fonctionne pas!!!!!
De plus, il est nécessaire de changer la configuration du spec_helper avec le lien suivant : Capybara.app_host = 'http://127.0.0.1:5984/traduxio/_design/traduxio/_rewrite'
N'oubliez pas de cloner le projet !
Des progrès ont été réalisés quant au test de validation CreateTranslation.
Pré-requis
La localisation de l’élément textarea n'a été rendue possible qu'en éditant le code source du fichier couchdb/_attachments/work.js
La ligne 261 existante :
var textarea=$("<textarea/>").addClass("fulltext").val(fulltext);
doit être remplacée comme suit (ajout d'un placeholder) :
var textarea=$("<textarea/>").addClass("fulltext").val(fulltext).attr("placeholder", "Enter your text here");
Evolution du test
Le nouveau test parvient à localiser l'élément, cependant, l'insertion de la première phrase de l'oeuvre originale n'est pas sauvegardée.
background do
visit '/works/'
click_on 'Ajouter une oeuvre'
fill_in 'title', :with => 'The Raven'
fill_in 'work-creator', :with => 'Edgar Allan Poe'
find('input[type="submit"][name=""]').click
sleep 5
first('.edit').click
fill_in ':placeholder => "Enter your text here"', :with => 'Once upon a midnight dreary, while I pondered, weak and weary, \n\n Over many a quaint an$
first('.edit').click
end
ERRATUM
La ligne 261 doit être remplacée comme suit :
var textarea=$("<textarea/>").addClass("fulltext").val(fulltext).prop("placeholder", "Enter your text here");
(propen lieu et place de attr)
Suite à la réunion du 22 mai, cette fonctionnalité est indiquée comme ayant une priorité haute. Sa mise en place permettrait d'éviter la multiplication des textes issus d'une même œuvre.
scenario 'Create a translation' do
find('.addVersion').click
within('#addPanel') do
first('input').set 'M. X'
find('input[type="submit"][value="Créer"]').click
end
sleep 2
first('input[type="button"][value="Lire"]').click
#fill_in first('input').set('Le corbeau')
#within('.meta.group') do
# select 'aa (Afar - Afar - Afaraf)', :from => first('select')
#end
#fill_in 'translator', :with => 'Martin Dupont'
sleep 5
expect(page).to have_content 'M. X'
Le test en background posait certains problèmes :
- Le textarea n'était jamais sauvegardé
- Le texte mis dans le textarea, malgré les \n n'allait pas à la ligne
- Le fill_in du placeholder ne semblait pas fonctionnel
Après installation de Selenium afin de savoir ce qu'il se passait réellement j'ai pu remarquer que :
- la seconde instruction find('.edit').click était fausse. Effectivement, selon jQuery il y a au moment de l'édition, 9 éléments ayant une classe edit, le premier étant un th, et donc pas le bouton qui nous intéresse.
- afin de pouvoir aller à la ligne, il est nécessaire d'utiliser des doubles quotes lors de l'écriture du texte et non pas des simples quotes qui feront que les \n ne seront pas interprétés.
- pour faire une recherche par placeholder, il faut ajouter après le find [:placeholder] afin de "charger" cette donnée
Le code contient encore un sleep 5, qui pourrait être réduit mais qui est nécessaire. Il faudrait augmenter la durée d'attente de Capybara (qui est par défaut à 5, il me semble)
Voici le code permettant de créer une version original :
background do
prefer_language 'fr'
visit '/works/'
click_on 'Ajouter une œuvre'
fill_in 'title', :with => 'The Raven'
fill_in 'work-creator', :with => 'Edgar Allan Poe'
find('input[type="submit"][name=""]').click
sleep 5
first('.edit').click
fill_in find('textarea[placeholder="Enter your text here"]')[:placeholder], :with => "Once upon a midnight dreary, while I pondered, weak and weary, \n\n Over many a quaint and..."
first('input.edit[type="button"]').click
end
Test de recette pour la création d'une traduction
require 'spec_helper'
feature 'Create a translation' do
background do
# Ajout d'une version originale afin de pouvoir ajouter une traduction
prefer_language 'fr'
visit '/works/'
click_on 'Ajouter une œuvre'
fill_in 'title', :with => 'The Raven zaeaze'
fill_in 'work-creator', :with => 'Edgar Allan Poe'
find('input[type="submit"][name=""]').click
sleep 5
first('.edit').click
fill_in find('textarea[placeholder="Enter your text here"]')[:placeholder], :with => "Once upon a midnight dreary, while I pondered, weak and weary, \n\n Over many a quaint and..."
first('input.edit[type="button"]').click
end
scenario 'Create a translation' do
find('.addVersion').click
sleep 3
within('#addPanel') do
first('input').set 'M. X'
find('input[type="submit"][value="Créer"]').click
end
# Récupération du bloc permettant d'ajouter des informations générales à la traduction
translation_header_bloc = page.find(:xpath, "//table[contains(@id,'hexapla')]/thead[contains(@class,'header')]/tr/th[contains(@class, 'edit')]/div")
within translation_header_bloc do
find('.title').set("Traduction 1")
find('.work-creator').set("Auteur 1")
within find('div.group') do
find("option[value='fr']").click # La méthode select serait plus appropriée ici mais il faut réussir à selectionner le select...
find('.date').set('2015')
end
end
# Remplissage des blocs
within select_edited_bloc(0) do
find('textarea.autosize').set("Il était une fois...")
end
within select_edited_bloc(1) do
find('textarea.autosize').set("Le reste de la traduction 1...")
end
# Récupération du "footer"
translation_header_footer_bloc = page.find(:xpath, "//table[contains(@id,'hexapla')]/thead[contains(@class,'footer')]/tr/th[contains(@class, 'edit')]/div")
within translation_header_footer_bloc do
find('input.edit[type="button"]').click
end
sleep 5
### Expectations ###
# Header
within translation_header_bloc do
expect(find('.title')).to have_content "Traduction 1"
expect(find('.work-creator')).to have_content "Auteur 1"
expect(find('.creator')).to have_content 'M. X'
within find('div.group') do
expect(find('.language')).to have_content "French"
expect(find('.date')).to have_content '2015'
end
end
# Bloc content
within select_bloc_by_version(0, 'M. X') do
expect(find('div.text')).to have_content "Il était une fois..."
end
within select_bloc_by_version(1, 'M. X') do
expect(find('div.text')).to have_content "Le reste de la traduction 1..."
end
end
# Permet de récupérer un bloc d'une version
# num - numéro du bloc (à partir de 0)
# version - nom de la version
def select_bloc_by_version(num, version)
page.find(:xpath, "//table[contains(@id,'hexapla')]/tbody/tr[contains(@data-line,'#{num}')]/td[contains(@data-version,'#{version}')]/div/div")
end
# Permet de récupérer un bloc en mode édition d'une version
# num - numéro du bloc (à partir de 0)
def select_edited_bloc(num)
page.find(:xpath, "//table[contains(@id,'hexapla')]/tbody/tr[contains(@data-line,'#{num}')]/td[contains(@class,'edit')]/div/div")
end
end
Le test ci-dessus est fonctionnel avec un driver selenium. Je rencontre cependant des problèmes avec le driver webkit utilisé par défaut par le projet.
Sous selenium subsiste une instabilité au niveau du dernier expect, parfois (de façon aléatoire) le div.text n'est pas trouvé
Sous webkit :
- find("option[value='fr']").click ne fonctionne pas, il faudrait trouver un moyen de trouver le select (en lui ajoutant un id/une classe par exemple ?)
- expect(find('.work-creator')).to have_content "Auteur 1" ne fonctionne pas, il considère que work-creator a pour contenu une chaine vide
- la même erreur que sous selenium pour le dernier expect
Je n'ai pas fait de pull request à cause des ces dysfonctionnements.
D'après l'historique du projet, cette fonctionnalité a été implémentée.
Par contre, je n'ai pas compris comment l'interface permettait de répondre aux scénarios 1 et 2 (ajouts de blocs).
La fonctionnalité est en ébauche. La branche n'est pas insérée dnas le tronc principal (https://github.com/franck-eyraud/TraduXio/tree/insert_blocks), du coup elle n'était pas déployé sur le site de test. Elle est maintenant déployée. On peut insérer des blocs en début et milieu de texte, mais pas en supprimer, et il manque l'insertion en fin de texte.