Merge pull request #9093 from demarches-simplifiees/rerouter-un-dossier

ETQ instructeur je peux réaffecter un dossier à un autre groupe d'instructeurs
This commit is contained in:
Eric Leroy-Terquem 2023-06-16 12:01:10 +00:00 committed by GitHub
commit be4f8f57ab
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
13 changed files with 132 additions and 4 deletions

View file

@ -331,6 +331,31 @@ module Instructeurs
end
end
def reaffectation
@dossier = current_instructeur.dossiers.find(params[:dossier_id])
@groupe_instructeur = @dossier.groupe_instructeur
@groupes_instructeurs = Kaminari.paginate_array(@groupe_instructeur.other_groupe_instructeurs)
.page(params[:page])
.per(ITEMS_PER_PAGE)
end
def reaffecter
dossier = current_instructeur.dossiers.find(params[:dossier_id])
new_group = dossier
.procedure
.groupe_instructeurs.find(params[:groupe_instructeur_id])
dossier.assign_to_groupe_instructeur(new_group)
dossier.update!(forced_groupe_instructeur: true)
flash.notice = t('instructeurs.dossiers.reaffectation', dossier_id: dossier.id, label: new_group.label)
redirect_to instructeur_procedure_path(procedure)
end
private
def dossier_scope

View file

@ -17,6 +17,7 @@
# en_construction_close_to_expiration_notice_sent_at :datetime
# en_instruction_at :datetime
# for_procedure_preview :boolean default(FALSE)
# forced_groupe_instructeur :boolean
# groupe_instructeur_updated_at :datetime
# hidden_at :datetime
# hidden_by_administration_at :datetime

View file

@ -27,9 +27,7 @@ class GroupeInstructeur < ApplicationRecord
validates :label, uniqueness: { scope: :procedure }
validates :closed, acceptance: { accept: [false] }, if: -> do
if closed
other_groupes = procedure.groupe_instructeurs - [self]
(other_groupes.map(&:closed) + [closed]).all?
(other_groupe_instructeurs.map(&:closed) + [closed]).all?
else
false
end
@ -92,6 +90,10 @@ class GroupeInstructeur < ApplicationRecord
!routing_rule_matches_tdc?
end
def other_groupe_instructeurs
procedure.groupe_instructeurs - [self]
end
private
def routing_rule_matches_tdc?

View file

@ -1,6 +1,7 @@
module RoutingEngine
def self.compute(dossier)
return if !dossier.procedure.feature_enabled?(:routing_rules)
return if dossier.forced_groupe_instructeur
matching_groupe = dossier.procedure.groupe_instructeurs.active.reject(&:routing_to_configure?).find do |gi|
gi.routing_rule&.compute(dossier.champs)

View file

@ -22,3 +22,7 @@
= dynamic_tab_item(t('views.instructeurs.dossiers.tab_steps.involved_persons'),
personnes_impliquees_instructeur_dossier_path(dossier.procedure, dossier))
- if dossier.procedure.routing_enabled? && dossier.procedure.feature_enabled?(:rerouting)
= dynamic_tab_item(t('views.instructeurs.dossiers.tab_steps.reaffectation'),
reaffectation_instructeur_dossier_path(dossier.procedure, dossier))

View file

@ -0,0 +1,24 @@
- content_for(:title, "Réaffectation · Dossier nº #{@dossier.id} (#{@dossier.owner_name})")
= render partial: "header", locals: { dossier: @dossier }
.container.groupe-instructeur
.card
.card-title Réaffectation du dossier nº #{@dossier.id} du groupe « #{@groupe_instructeur.label} »
%p
Vous pouvez réaffecter le dossier nº #{@dossier.id} à l'un des groupes d'instructeurs suivants.
%table.table.mt-2
%thead
%tr
%th{ colspan: 2 }= t("instructeurs.dossiers.existing_groupe", count: @groupes_instructeurs.total_count)
%tbody
- @groupes_instructeurs.each do |group|
%tr
%td= group.label
%td.actions= button_to 'Réaffecter le dossier à ce groupe',
reaffecter_instructeur_dossier_path(procedure_id: @dossier.procedure.id, dossier_id: @dossier.id, groupe_instructeur_id: group.id),
{ class: 'button',
data: { confirm: "Êtes-vous sûr de vouloir réaffecter le dossier nº #{@dossier.id} du groupe « #{@groupe_instructeur.label} » vers le groupe  « #{group.label} » ?" } }
= paginate @groupes_instructeurs, views_prefix: 'shared'

View file

@ -37,3 +37,19 @@
- if champs.any? || dossier.procedure.routing_enabled?
.card
= render partial: "shared/dossiers/champs", locals: { champs: champs, dossier: dossier, demande_seen_at: demande_seen_at, profile: profile }
- if dossier.procedure.routing_enabled?
%h2.fr-h6
Réaffectation
.card
En cas d'erreur de l'usager, vous pouvez réaffecter le dossier vers l'un des groupes d'instructeurs suivants
= form_tag reaffecter_instructeur_dossier_path(procedure_id: @dossier.procedure.id, dossier_id: @dossier.id),
method: :post,
class: 'fr-mb-3w mt-2' do
.flex
= select_tag(:groupe_instructeur_id,
options_for_select(@dossier.groupe_instructeur.other_groupe_instructeurs.pluck(:label, :id)),
include_blank: true,
class: 'fr-select flex auto fr-mr-2w')
= button_tag 'Réaffecter', class: 'fr-btn fr-btn--secondary'

View file

@ -18,7 +18,8 @@ features = [
:hide_instructeur_email,
:procedure_routage_api,
:routing_rules,
:groupe_instructeur_api_hack
:groupe_instructeur_api_hack,
:rerouting
]
def database_exists?

View file

@ -356,6 +356,7 @@ en:
external_opinion: External opinion
messaging: Messaging
involved_persons: Involved persons
reaffectation: reassignment
tab_explainations:
a_suivre: No instructor is assigned to follow up on these files. Be the first !
suivis: The folders that are in this tab are only those that you follow. You can exchange with the requester until you can accept them, refuse them or classify them without follow-up.

View file

@ -356,6 +356,7 @@ fr:
external_opinion: Avis externes
messaging: Messagerie
involved_persons: Personnes impliquées
reaffectation: Réaffectation
tab_explainations:
a_suivre: Aucun instructeur nest affecté au suivi de ces dossiers. Soyez le premier !
suivis: Les dossiers qui sont dans cet onglet sont uniquement ceux que vous suivez. Vous pouvez échanger avec le demandeur jusquà pouvoir les accepter, les refuser ou les classer sans suite.
@ -786,6 +787,10 @@ fr:
deleted_by_instructeur: "Le dossier a bien été supprimé de votre interface"
impossible_deletion: "Supression impossible : le dossier nest pas traité"
restore: "Le dossier a bien été restauré"
reaffectation: "Le dossier nº %{dossier_id} a été réaffecté au groupe dinstructeurs « %{label} »."
existing_groupe:
one: "%{count} groupe existe"
other: "%{count} groupes existent"
labels:
to_follow: à suivre
total: dossiers

View file

@ -450,6 +450,8 @@ Rails.application.routes.draw do
post 'avis' => 'dossiers#create_avis'
get 'print' => 'dossiers#print'
get 'telecharger_pjs' => 'dossiers#telecharger_pjs'
get 'reaffectation'
post 'reaffecter'
end
end

View file

@ -0,0 +1,5 @@
class AddForcedGroupeInstructeurToDossier < ActiveRecord::Migration[7.0]
def change
add_column :dossiers, :forced_groupe_instructeur, :boolean, default: false, null: false
end
end

View file

@ -1151,4 +1151,45 @@ describe Instructeurs::DossiersController, type: :controller do
it { expect(flash.alert).to eq("Votre action n'a pas été effectuée, ce dossier fait parti d'un traitement de masse.") }
end
end
describe '#reaffectation' do
let!(:gi_2) { GroupeInstructeur.create(label: 'deuxième groupe', procedure: procedure) }
let!(:gi_3) { GroupeInstructeur.create(label: 'troisième groupe', procedure: procedure) }
let!(:dossier) { create(:dossier, :en_construction, procedure: procedure, groupe_instructeur: procedure.groupe_instructeurs.first) }
before do
post :reaffectation,
params: {
procedure_id: procedure.id,
dossier_id: dossier.id
}
end
it do
expect(response).to have_http_status(:ok)
expect(response.body).to include("Vous pouvez réaffecter le dossier nº #{dossier.id} à l'un des groupes d'instructeurs suivants.")
expect(response.body).to include('2 groupes existent')
end
end
describe '#reaffecter' do
let!(:gi_2) { GroupeInstructeur.create(label: 'deuxième groupe', procedure: procedure) }
let!(:dossier) { create(:dossier, :en_construction, procedure: procedure, groupe_instructeur: procedure.groupe_instructeurs.first) }
before do
post :reaffecter,
params: {
procedure_id: procedure.id,
dossier_id: dossier.id,
groupe_instructeur_id: gi_2.id
}
end
it do
expect(dossier.reload.groupe_instructeur.id).to eq(gi_2.id)
expect(dossier.forced_groupe_instructeur).to be_truthy
expect(response).to redirect_to(instructeur_procedure_path(procedure))
expect(flash.notice).to eq("Le dossier nº #{dossier.id} a été réaffecté au groupe dinstructeurs « deuxième groupe ».")
end
end
end