commit
2b922934c7
27 changed files with 323 additions and 53 deletions
|
@ -29,6 +29,9 @@ module CreateAvisConcern
|
||||||
if persisted.any?
|
if persisted.any?
|
||||||
sent_emails_addresses = persisted.map(&:email_to_display).join(", ")
|
sent_emails_addresses = persisted.map(&:email_to_display).join(", ")
|
||||||
flash.notice = "Une demande d'avis a été envoyée à #{sent_emails_addresses}"
|
flash.notice = "Une demande d'avis a été envoyée à #{sent_emails_addresses}"
|
||||||
|
persisted.each do |avis|
|
||||||
|
dossier.demander_un_avis!(avis)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
if failed.any?
|
if failed.any?
|
||||||
|
|
|
@ -136,8 +136,8 @@ module Gestionnaires
|
||||||
|
|
||||||
def update_annotations
|
def update_annotations
|
||||||
dossier = current_gestionnaire.dossiers.includes(champs_private: :type_de_champ).find(params[:dossier_id])
|
dossier = current_gestionnaire.dossiers.includes(champs_private: :type_de_champ).find(params[:dossier_id])
|
||||||
# FIXME: add attachements validation, cf. Champ#piece_justificative_file_errors
|
|
||||||
dossier.update(champs_private_params)
|
dossier.update(champs_private_params)
|
||||||
|
dossier.modifier_annotations!(current_gestionnaire)
|
||||||
redirect_to annotations_privees_gestionnaire_dossier_path(procedure, dossier)
|
redirect_to annotations_privees_gestionnaire_dossier_path(procedure, dossier)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import { sortableElement, sortableHandle } from 'react-sortable-hoc';
|
import { sortableElement, sortableHandle } from 'react-sortable-hoc';
|
||||||
|
import { useInView } from 'react-intersection-observer';
|
||||||
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
||||||
|
|
||||||
import DescriptionInput from './DescriptionInput';
|
import DescriptionInput from './DescriptionInput';
|
||||||
|
@ -29,6 +30,10 @@ const TypeDeChamp = sortableElement(
|
||||||
const canBeMandatory =
|
const canBeMandatory =
|
||||||
!isHeaderSection && !isExplication && !state.isAnnotation;
|
!isHeaderSection && !isExplication && !state.isAnnotation;
|
||||||
|
|
||||||
|
const [ref, inView] = useInView({
|
||||||
|
threshold: [0.6]
|
||||||
|
});
|
||||||
|
|
||||||
const updateHandlers = createUpdateHandlers(
|
const updateHandlers = createUpdateHandlers(
|
||||||
dispatch,
|
dispatch,
|
||||||
typeDeChamp,
|
typeDeChamp,
|
||||||
|
@ -42,8 +47,10 @@ const TypeDeChamp = sortableElement(
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
ref={isLastItem ? state.lastTypeDeChampRef : null}
|
ref={ref}
|
||||||
data-index={index}
|
data-index={index}
|
||||||
|
data-in-view={inView ? true : undefined}
|
||||||
|
data-repetition={isRepetition ? true : undefined}
|
||||||
className={`type-de-champ form flex column justify-start ${
|
className={`type-de-champ form flex column justify-start ${
|
||||||
isHeaderSection ? 'type-header-section' : ''
|
isHeaderSection ? 'type-header-section' : ''
|
||||||
}`}
|
}`}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import React, { useReducer, useRef } from 'react';
|
import React, { useReducer } from 'react';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
||||||
|
|
||||||
|
@ -11,11 +11,7 @@ function TypeDeChampRepetitionOptions({
|
||||||
state: parentState,
|
state: parentState,
|
||||||
typeDeChamp
|
typeDeChamp
|
||||||
}) {
|
}) {
|
||||||
const lastTypeDeChampRef = useRef(null);
|
const [state, dispatch] = useReducer(typeDeChampsReducer, parentState);
|
||||||
const [state, dispatch] = useReducer(typeDeChampsReducer, {
|
|
||||||
...parentState,
|
|
||||||
lastTypeDeChampRef
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isVisible) {
|
if (isVisible) {
|
||||||
return (
|
return (
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import React, { useReducer, useRef } from 'react';
|
import React, { useReducer } from 'react';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
|
||||||
|
|
||||||
|
@ -7,10 +7,8 @@ import TypeDeChamp from './TypeDeChamp';
|
||||||
import typeDeChampsReducer from '../typeDeChampsReducer';
|
import typeDeChampsReducer from '../typeDeChampsReducer';
|
||||||
|
|
||||||
function TypeDeChamps({ state: rootState, typeDeChamps }) {
|
function TypeDeChamps({ state: rootState, typeDeChamps }) {
|
||||||
const lastTypeDeChampRef = useRef(null);
|
|
||||||
const [state, dispatch] = useReducer(typeDeChampsReducer, {
|
const [state, dispatch] = useReducer(typeDeChampsReducer, {
|
||||||
...rootState,
|
...rootState,
|
||||||
lastTypeDeChampRef,
|
|
||||||
typeDeChamps
|
typeDeChamps
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -37,30 +37,52 @@ export default function typeDeChampsReducer(state, { type, params, done }) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function addNewTypeDeChamp(state, typeDeChamps, done) {
|
function addTypeDeChamp(state, typeDeChamps, insertAfter, done) {
|
||||||
const typeDeChamp = {
|
const typeDeChamp = {
|
||||||
...state.defaultTypeDeChampAttributes,
|
...state.defaultTypeDeChampAttributes,
|
||||||
order_place: typeDeChamps.length
|
order_place: typeDeChamps.length
|
||||||
};
|
};
|
||||||
|
|
||||||
createTypeDeChampOperation(typeDeChamp, state.queue)
|
createTypeDeChampOperation(typeDeChamp, state.queue)
|
||||||
.then(() => {
|
.then(async () => {
|
||||||
|
if (insertAfter) {
|
||||||
|
// Move the champ to the correct position server-side
|
||||||
|
await moveTypeDeChampOperation(
|
||||||
|
typeDeChamp,
|
||||||
|
insertAfter.index,
|
||||||
|
state.queue
|
||||||
|
);
|
||||||
|
}
|
||||||
state.flash.success();
|
state.flash.success();
|
||||||
done();
|
done();
|
||||||
if (state.lastTypeDeChampRef) {
|
if (insertAfter) {
|
||||||
scrollToComponent(state.lastTypeDeChampRef.current);
|
scrollToComponent(insertAfter.target.nextElementSibling);
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.catch(message => state.flash.error(message));
|
.catch(message => state.flash.error(message));
|
||||||
|
|
||||||
|
let newTypeDeChamps = [...typeDeChamps, typeDeChamp];
|
||||||
|
if (insertAfter) {
|
||||||
|
// Move the champ to the correct position client-side
|
||||||
|
newTypeDeChamps = arrayMove(
|
||||||
|
newTypeDeChamps,
|
||||||
|
typeDeChamps.length,
|
||||||
|
insertAfter.index
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
...state,
|
...state,
|
||||||
typeDeChamps: [...typeDeChamps, typeDeChamp]
|
typeDeChamps: newTypeDeChamps
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function addNewTypeDeChamp(state, typeDeChamps, done) {
|
||||||
|
return addTypeDeChamp(state, typeDeChamps, findItemToInsertAfter(), done);
|
||||||
|
}
|
||||||
|
|
||||||
function addNewRepetitionTypeDeChamp(state, typeDeChamps, typeDeChamp, done) {
|
function addNewRepetitionTypeDeChamp(state, typeDeChamps, typeDeChamp, done) {
|
||||||
return addNewTypeDeChamp(
|
return addTypeDeChamp(
|
||||||
{
|
{
|
||||||
...state,
|
...state,
|
||||||
defaultTypeDeChampAttributes: {
|
defaultTypeDeChampAttributes: {
|
||||||
|
@ -69,6 +91,7 @@ function addNewRepetitionTypeDeChamp(state, typeDeChamps, typeDeChamp, done) {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
typeDeChamps,
|
typeDeChamps,
|
||||||
|
null,
|
||||||
done
|
done
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -182,3 +205,23 @@ function getUpdateHandler(typeDeChamp, { queue, flash }) {
|
||||||
}
|
}
|
||||||
return handler;
|
return handler;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function findItemToInsertAfter() {
|
||||||
|
const target = getFirstTarget();
|
||||||
|
|
||||||
|
return {
|
||||||
|
target,
|
||||||
|
index: parseInt(target.dataset.index) + 1
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
function getFirstTarget() {
|
||||||
|
const [target] = document.querySelectorAll('[data-in-view]');
|
||||||
|
if (target) {
|
||||||
|
const parentTarget = target.closest('[data-repetition]');
|
||||||
|
if (parentTarget) {
|
||||||
|
return parentTarget;
|
||||||
|
}
|
||||||
|
return target;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -5,3 +5,7 @@ import '@babel/polyfill';
|
||||||
import 'dom4';
|
import 'dom4';
|
||||||
import './polyfills/insertAdjacentElement';
|
import './polyfills/insertAdjacentElement';
|
||||||
import './polyfills/dataset';
|
import './polyfills/dataset';
|
||||||
|
|
||||||
|
if (typeof window.IntersectionObserver === 'undefined') {
|
||||||
|
import('intersection-observer');
|
||||||
|
}
|
||||||
|
|
|
@ -288,7 +288,7 @@ class Dossier < ApplicationRecord
|
||||||
def passer_automatiquement_en_instruction!
|
def passer_automatiquement_en_instruction!
|
||||||
en_instruction!
|
en_instruction!
|
||||||
|
|
||||||
log_dossier_operation(nil, :passer_en_instruction, automatic_operation: true)
|
log_automatic_dossier_operation(:passer_en_instruction)
|
||||||
end
|
end
|
||||||
|
|
||||||
def repasser_en_construction!(gestionnaire)
|
def repasser_en_construction!(gestionnaire)
|
||||||
|
@ -311,7 +311,7 @@ class Dossier < ApplicationRecord
|
||||||
end
|
end
|
||||||
|
|
||||||
NotificationMailer.send_closed_notification(self).deliver_later
|
NotificationMailer.send_closed_notification(self).deliver_later
|
||||||
log_dossier_operation(gestionnaire, :accepter)
|
log_dossier_operation(gestionnaire, :accepter, self)
|
||||||
end
|
end
|
||||||
|
|
||||||
def accepter_automatiquement!
|
def accepter_automatiquement!
|
||||||
|
@ -324,14 +324,14 @@ class Dossier < ApplicationRecord
|
||||||
end
|
end
|
||||||
|
|
||||||
NotificationMailer.send_closed_notification(self).deliver_later
|
NotificationMailer.send_closed_notification(self).deliver_later
|
||||||
log_dossier_operation(nil, :accepter, automatic_operation: true)
|
log_automatic_dossier_operation(:accepter, self)
|
||||||
end
|
end
|
||||||
|
|
||||||
def hide!(administration)
|
def hide!(administration)
|
||||||
update(hidden_at: Time.zone.now)
|
update(hidden_at: Time.zone.now)
|
||||||
|
|
||||||
log_administration_dossier_operation(administration, :supprimer)
|
|
||||||
DeletedDossier.create_from_dossier(self)
|
DeletedDossier.create_from_dossier(self)
|
||||||
|
log_dossier_operation(administration, :supprimer, self)
|
||||||
end
|
end
|
||||||
|
|
||||||
def refuser!(gestionnaire, motivation, justificatif = nil)
|
def refuser!(gestionnaire, motivation, justificatif = nil)
|
||||||
|
@ -343,7 +343,7 @@ class Dossier < ApplicationRecord
|
||||||
refuse!
|
refuse!
|
||||||
|
|
||||||
NotificationMailer.send_refused_notification(self).deliver_later
|
NotificationMailer.send_refused_notification(self).deliver_later
|
||||||
log_dossier_operation(gestionnaire, :refuser)
|
log_dossier_operation(gestionnaire, :refuser, self)
|
||||||
end
|
end
|
||||||
|
|
||||||
def classer_sans_suite!(gestionnaire, motivation, justificatif = nil)
|
def classer_sans_suite!(gestionnaire, motivation, justificatif = nil)
|
||||||
|
@ -355,7 +355,7 @@ class Dossier < ApplicationRecord
|
||||||
sans_suite!
|
sans_suite!
|
||||||
|
|
||||||
NotificationMailer.send_without_continuation_notification(self).deliver_later
|
NotificationMailer.send_without_continuation_notification(self).deliver_later
|
||||||
log_dossier_operation(gestionnaire, :classer_sans_suite)
|
log_dossier_operation(gestionnaire, :classer_sans_suite, self)
|
||||||
end
|
end
|
||||||
|
|
||||||
def check_mandatory_champs
|
def check_mandatory_champs
|
||||||
|
@ -366,20 +366,33 @@ class Dossier < ApplicationRecord
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def modifier_annotations!(gestionnaire)
|
||||||
|
champs_private.select(&:value_previously_changed?).each do |champ|
|
||||||
|
log_dossier_operation(gestionnaire, :modifier_annotation, champ)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def demander_un_avis!(avis)
|
||||||
|
log_dossier_operation(avis.claimant, :demander_un_avis, avis)
|
||||||
|
end
|
||||||
|
|
||||||
private
|
private
|
||||||
|
|
||||||
def log_dossier_operation(gestionnaire, operation, automatic_operation: false)
|
def log_dossier_operation(author, operation, subject = nil)
|
||||||
dossier_operation_logs.create(
|
DossierOperationLog.create_and_serialize(
|
||||||
gestionnaire: gestionnaire,
|
dossier: self,
|
||||||
operation: DossierOperationLog.operations.fetch(operation),
|
operation: DossierOperationLog.operations.fetch(operation),
|
||||||
automatic_operation: automatic_operation
|
author: author,
|
||||||
|
subject: subject
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
def log_administration_dossier_operation(administration, operation)
|
def log_automatic_dossier_operation(operation, subject = nil)
|
||||||
dossier_operation_logs.create(
|
DossierOperationLog.create_and_serialize(
|
||||||
administration: administration,
|
dossier: self,
|
||||||
operation: DossierOperationLog.operations.fetch(operation)
|
operation: DossierOperationLog.operations.fetch(operation),
|
||||||
|
automatic_operation: true,
|
||||||
|
subject: subject
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -5,10 +5,76 @@ class DossierOperationLog < ApplicationRecord
|
||||||
accepter: 'accepter',
|
accepter: 'accepter',
|
||||||
refuser: 'refuser',
|
refuser: 'refuser',
|
||||||
classer_sans_suite: 'classer_sans_suite',
|
classer_sans_suite: 'classer_sans_suite',
|
||||||
supprimer: 'supprimer'
|
supprimer: 'supprimer',
|
||||||
|
modifier_annotation: 'modifier_annotation',
|
||||||
|
demander_un_avis: 'demander_un_avis'
|
||||||
}
|
}
|
||||||
|
|
||||||
belongs_to :dossier
|
belongs_to :dossier
|
||||||
belongs_to :gestionnaire
|
has_one_attached :serialized
|
||||||
belongs_to :administration
|
|
||||||
|
def self.create_and_serialize(params)
|
||||||
|
dossier = params.fetch(:dossier)
|
||||||
|
|
||||||
|
duree_conservation_dossiers = dossier.procedure.duree_conservation_dossiers_dans_ds
|
||||||
|
keep_until = if duree_conservation_dossiers.present?
|
||||||
|
if dossier.en_instruction_at
|
||||||
|
dossier.en_instruction_at + duree_conservation_dossiers.months
|
||||||
|
else
|
||||||
|
dossier.created_at + duree_conservation_dossiers.months
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
operation_log = new(operation: params.fetch(:operation),
|
||||||
|
dossier_id: dossier.id,
|
||||||
|
keep_until: keep_until,
|
||||||
|
executed_at: Time.zone.now,
|
||||||
|
automatic_operation: !!params[:automatic_operation])
|
||||||
|
|
||||||
|
serialized = {
|
||||||
|
operation: operation_log.operation,
|
||||||
|
dossier_id: operation_log.dossier_id,
|
||||||
|
author: self.serialize_author(params[:author]),
|
||||||
|
subject: self.serialize_subject(params[:subject]),
|
||||||
|
automatic_operation: operation_log.automatic_operation?,
|
||||||
|
executed_at: operation_log.executed_at.iso8601
|
||||||
|
}.compact.to_json
|
||||||
|
|
||||||
|
operation_log.digest = Digest::SHA256.hexdigest(serialized)
|
||||||
|
|
||||||
|
operation_log.serialized.attach(
|
||||||
|
io: StringIO.new(serialized),
|
||||||
|
filename: "operation-#{operation_log.digest}.json",
|
||||||
|
content_type: 'application/json',
|
||||||
|
# we don't want to run virus scanner on this file
|
||||||
|
metadata: { virus_scan_result: ActiveStorage::VirusScanner::SAFE }
|
||||||
|
)
|
||||||
|
|
||||||
|
operation_log.save!
|
||||||
|
end
|
||||||
|
|
||||||
|
def self.serialize_author(author)
|
||||||
|
if author.nil?
|
||||||
|
nil
|
||||||
|
else
|
||||||
|
OperationAuthorSerializer.new(author).as_json
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def self.serialize_subject(subject)
|
||||||
|
if subject.nil?
|
||||||
|
nil
|
||||||
|
elsif !Flipflop.operation_log_serialize_subject?
|
||||||
|
{ id: subject.id }
|
||||||
|
else
|
||||||
|
case subject
|
||||||
|
when Dossier
|
||||||
|
DossierSerializer.new(subject).as_json
|
||||||
|
when Champ
|
||||||
|
ChampSerializer.new(subject).as_json
|
||||||
|
when Avis
|
||||||
|
AvisSerializer.new(subject).as_json
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
19
app/serializers/avis_serializer.rb
Normal file
19
app/serializers/avis_serializer.rb
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
class AvisSerializer < ActiveModel::Serializer
|
||||||
|
attributes :email,
|
||||||
|
:answer,
|
||||||
|
:introduction,
|
||||||
|
:created_at,
|
||||||
|
:answered_at
|
||||||
|
|
||||||
|
def email
|
||||||
|
object.email_to_display
|
||||||
|
end
|
||||||
|
|
||||||
|
def created_at
|
||||||
|
object.created_at&.in_time_zone('UTC')
|
||||||
|
end
|
||||||
|
|
||||||
|
def answered_at
|
||||||
|
object.updated_at&.in_time_zone('UTC')
|
||||||
|
end
|
||||||
|
end
|
18
app/serializers/operation_author_serializer.rb
Normal file
18
app/serializers/operation_author_serializer.rb
Normal file
|
@ -0,0 +1,18 @@
|
||||||
|
class OperationAuthorSerializer < ActiveModel::Serializer
|
||||||
|
attributes :id, :email
|
||||||
|
|
||||||
|
def id
|
||||||
|
case object
|
||||||
|
when User
|
||||||
|
"Usager##{object.id}"
|
||||||
|
when Gestionnaire
|
||||||
|
"Instructeur##{object.id}"
|
||||||
|
when Administrateur
|
||||||
|
"Administrateur##{object.id}"
|
||||||
|
when Administration
|
||||||
|
"Manager##{object.id}"
|
||||||
|
else
|
||||||
|
nil
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
|
@ -30,7 +30,7 @@
|
||||||
%li Texte de loi (loi, décret, circulaire, arrêté,…)
|
%li Texte de loi (loi, décret, circulaire, arrêté,…)
|
||||||
%li Texte juridique (statuts, délibération, décision du conseil d'administration…)
|
%li Texte juridique (statuts, délibération, décision du conseil d'administration…)
|
||||||
%li
|
%li
|
||||||
= link_to("En savoir plus", CADRE_JURIDIQUE_URL, target: "_blank", rel: "noopener")
|
= link_to("En savoir plus avec cette vidéo de 5 minutes", CADRE_JURIDIQUE_URL, target: "_blank", rel: "noopener")
|
||||||
|
|
||||||
%p.help-block
|
%p.help-block
|
||||||
%i.fa.fa-info-circle
|
%i.fa.fa-info-circle
|
||||||
|
|
|
@ -31,6 +31,13 @@
|
||||||
%br
|
%br
|
||||||
.alert.alert-info
|
.alert.alert-info
|
||||||
Attention, diffusez toujours le <strong>lien complet</strong> affiché ci-dessus, et non pas un lien générique vers demarches-simplifiees.fr. Ne dites pas non plus aux usagers de se rendre sur le site générique demarches-simplifiees.fr, donnez-leur toujours le lien complet.
|
Attention, diffusez toujours le <strong>lien complet</strong> affiché ci-dessus, et non pas un lien générique vers demarches-simplifiees.fr. Ne dites pas non plus aux usagers de se rendre sur le site générique demarches-simplifiees.fr, donnez-leur toujours le lien complet.
|
||||||
|
%br
|
||||||
|
%br
|
||||||
|
Prenez quelques minutes pour savoir comment établir une bonne relation avec les usagers de votre démarche :
|
||||||
|
= link_to "Regarder la vidéo de 5 minutes",
|
||||||
|
"https://vimeo.com/334463514",
|
||||||
|
target: "_blank"
|
||||||
|
|
||||||
#path-messages
|
#path-messages
|
||||||
#path_is_mine.text-warning.center.message
|
#path_is_mine.text-warning.center.message
|
||||||
Ce lien est déjà utilisé par une de vos démarche.
|
Ce lien est déjà utilisé par une de vos démarche.
|
||||||
|
|
|
@ -2,9 +2,35 @@
|
||||||
- if current_administrateur.procedures.brouillons.count == 0
|
- if current_administrateur.procedures.brouillons.count == 0
|
||||||
.card.feedback
|
.card.feedback
|
||||||
.card-title
|
.card-title
|
||||||
Bienvenue,
|
Bienvenue,
|
||||||
|
%br
|
||||||
vous allez pouvoir créer une première démarche de test.
|
vous allez pouvoir créer une première démarche de test.
|
||||||
Celle-ci sera visible uniquement par vous et ne sera publiée nulle part, alors pas de crainte à avoir.
|
Celle-ci sera visible uniquement par vous et ne sera publiée nulle part, alors pas de crainte à avoir.
|
||||||
|
%br
|
||||||
|
%br
|
||||||
|
Besoin d'aide ?
|
||||||
|
%br
|
||||||
|
> Nous proposons des ateliers en ligne pour vous aider à créer votre 1er formulaire et répondre à vos questions :
|
||||||
|
= link_to "inscrivez-vous ici",
|
||||||
|
"https://vimeo.com/334463514",
|
||||||
|
target: "_blank"
|
||||||
|
%br
|
||||||
|
> Vous pouvez
|
||||||
|
= link_to "visionner cette vidéo",
|
||||||
|
"https://vimeo.com/261478872",
|
||||||
|
target: "_blank"
|
||||||
|
%br
|
||||||
|
> Vous pouvez lire notre
|
||||||
|
= link_to "documentation en ligne",
|
||||||
|
"https://doc.demarches-simplifiees.fr/tutoriels/tutoriel-administrateur",
|
||||||
|
target: "_blank"
|
||||||
|
|
||||||
|
%br
|
||||||
|
> Vous pouvez enfin
|
||||||
|
= link_to "prendre un rendez-vous téléphonique avec nous",
|
||||||
|
"https://calendly.com/demarches-simplifiees/accompagnement-administrateur-demarches-simplifiees-fr",
|
||||||
|
target: "_blank"
|
||||||
|
|
||||||
|
|
||||||
.form
|
.form
|
||||||
.send-wrapper
|
.send-wrapper
|
||||||
|
|
|
@ -81,6 +81,11 @@
|
||||||
%p
|
%p
|
||||||
Une fois que vous êtes prêt à publier définitivement votre démarche, cliquez sur le bouton "Publier" pour choisir le lien définitif de votre démarche, les modifications sur la démarches ne seront alors plus possibles.
|
Une fois que vous êtes prêt à publier définitivement votre démarche, cliquez sur le bouton "Publier" pour choisir le lien définitif de votre démarche, les modifications sur la démarches ne seront alors plus possibles.
|
||||||
|
|
||||||
|
%br
|
||||||
|
%h4 Prenez quelques minutes pour savoir comment établir une bonne relation avec les usagers de votre démarche:
|
||||||
|
%p.center
|
||||||
|
%br
|
||||||
|
%iframe{ :src =>"https://player.vimeo.com/video/334463514?color=0069CC",:width =>"640",:height =>"360",:frameborder => "0" }
|
||||||
- else
|
- else
|
||||||
.alert.alert-info
|
.alert.alert-info
|
||||||
Pour pouvoir tester cette démarche, vous devez d’abord lui affecter
|
Pour pouvoir tester cette démarche, vous devez d’abord lui affecter
|
||||||
|
|
|
@ -13,4 +13,6 @@
|
||||||
\-
|
\-
|
||||||
= link_to 'Documentation', DOC_URL
|
= link_to 'Documentation', DOC_URL
|
||||||
\-
|
\-
|
||||||
= link_to 'Aide', FAQ_URL
|
= link_to 'FAQ', FAQ_ADMIN_URL
|
||||||
|
\-
|
||||||
|
= link_to 'Inscription ateliers en ligne', WEBINAIRE_URL
|
||||||
|
|
|
@ -10,7 +10,7 @@
|
||||||
#navbar-body
|
#navbar-body
|
||||||
.row
|
.row
|
||||||
%div{ style: "vertical-align: middle;float:left;position:absolute;line-height: 60px;z-index:2;" }
|
%div{ style: "vertical-align: middle;float:left;position:absolute;line-height: 60px;z-index:2;" }
|
||||||
Besoin d'aide ? <a href="tel:#{CONTACT_PHONE}">#{CONTACT_PHONE}</a> ou <a href="#{contact_admin_path}" target="_blank" rel="noopener">par email</a>
|
Besoin d'aide? <a href="tel:#{CONTACT_PHONE}">#{CONTACT_PHONE}</a> ou <a href="#{contact_admin_path}" target="_blank" rel="noopener">email</a> ou <a target="_blank" rel="noopener" href="https://calendly.com/demarches-simplifiees/accompagnement-administrateur-demarches-simplifiees-fr">prenez rendez-vous avec nous</a>
|
||||||
-# BEST WTF EVER
|
-# BEST WTF EVER
|
||||||
-# this begin rescue hides potentials bugs by displaying another navbar
|
-# this begin rescue hides potentials bugs by displaying another navbar
|
||||||
- begin
|
- begin
|
||||||
|
|
|
@ -11,7 +11,7 @@ by providing a `content_for(:javascript)` block.
|
||||||
<%= javascript_include_tag js_path %>
|
<%= javascript_include_tag js_path %>
|
||||||
<% end %>
|
<% end %>
|
||||||
|
|
||||||
<%= javascript_pack_tag 'manager' %>
|
<%= javascript_packs_with_chunks_tag 'manager' %>
|
||||||
|
|
||||||
<%= yield :javascript %>
|
<%= yield :javascript %>
|
||||||
|
|
||||||
|
|
|
@ -17,6 +17,8 @@ Flipflop.configure do
|
||||||
feature :enable_email_login_token
|
feature :enable_email_login_token
|
||||||
feature :new_champs_editor
|
feature :new_champs_editor
|
||||||
|
|
||||||
|
feature :operation_log_serialize_subject
|
||||||
|
|
||||||
group :production do
|
group :production do
|
||||||
feature :remote_storage,
|
feature :remote_storage,
|
||||||
default: ENV['FOG_ENABLED'] == 'enabled'
|
default: ENV['FOG_ENABLED'] == 'enabled'
|
||||||
|
|
|
@ -15,13 +15,14 @@ FOG_BASE_URL = "https://static.demarches-simplifiees.fr"
|
||||||
DOC_URL = "https://doc.demarches-simplifiees.fr"
|
DOC_URL = "https://doc.demarches-simplifiees.fr"
|
||||||
ADMINISTRATEUR_TUTORIAL_URL = [DOC_URL, "tutoriels", "tutoriel-administrateur"].join("/")
|
ADMINISTRATEUR_TUTORIAL_URL = [DOC_URL, "tutoriels", "tutoriel-administrateur"].join("/")
|
||||||
INSTRUCTEUR_TUTORIAL_URL = [DOC_URL, "tutoriels", "tutoriel-accompagnateur"].join("/")
|
INSTRUCTEUR_TUTORIAL_URL = [DOC_URL, "tutoriels", "tutoriel-accompagnateur"].join("/")
|
||||||
CADRE_JURIDIQUE_URL = [ADMINISTRATEUR_TUTORIAL_URL, "cadre-juridique"].join("#")
|
CADRE_JURIDIQUE_URL = [DOC_URL, "tutoriels/video-le-cadre-juridique"].join("/")
|
||||||
WEBINAIRE_URL = [DOC_URL, "pour-aller-plus-loin", "webinaires"].join("/")
|
WEBINAIRE_URL = "https://app.livestorm.co/demarches-simplifiees"
|
||||||
LISTE_DES_DEMARCHES_URL = [DOC_URL, "listes-des-demarches"].join("/")
|
LISTE_DES_DEMARCHES_URL = [DOC_URL, "listes-des-demarches"].join("/")
|
||||||
CGU_URL = [DOC_URL, "cgu"].join("/")
|
CGU_URL = [DOC_URL, "cgu"].join("/")
|
||||||
MENTIONS_LEGALES_URL = [CGU_URL, "4-mentions-legales"].join("#")
|
MENTIONS_LEGALES_URL = [CGU_URL, "4-mentions-legales"].join("#")
|
||||||
API_DOC_URL = [DOC_URL, "pour-aller-plus-loin", "api"].join("/")
|
API_DOC_URL = [DOC_URL, "pour-aller-plus-loin", "api"].join("/")
|
||||||
WEBHOOK_DOC_URL = [DOC_URL, "pour-aller-plus-loin", "webhook"].join("/")
|
WEBHOOK_DOC_URL = [DOC_URL, "pour-aller-plus-loin", "webhook"].join("/")
|
||||||
FAQ_URL = "https://faq.demarches-simplifiees.fr"
|
FAQ_URL = "https://faq.demarches-simplifiees.fr"
|
||||||
|
FAQ_ADMIN_URL = "https://faq.demarches-simplifiees.fr/collection/1-administrateur"
|
||||||
STATUS_PAGE_URL = "https://status.demarches-simplifiees.fr"
|
STATUS_PAGE_URL = "https://status.demarches-simplifiees.fr"
|
||||||
MATOMO_IFRAME_URL = "https://stats.data.gouv.fr/index.php?module=CoreAdminHome&action=optOut&language=fr&&fontColor=333333&fontSize=16px&fontFamily=Muli"
|
MATOMO_IFRAME_URL = "https://stats.data.gouv.fr/index.php?module=CoreAdminHome&action=optOut&language=fr&&fontColor=333333&fontSize=16px&fontFamily=Muli"
|
||||||
|
|
|
@ -0,0 +1,8 @@
|
||||||
|
class AddDigestAndTimestampsToDossierOperationLogs < ActiveRecord::Migration[5.2]
|
||||||
|
def change
|
||||||
|
add_column :dossier_operation_logs, :keep_until, :datetime
|
||||||
|
add_column :dossier_operation_logs, :executed_at, :datetime
|
||||||
|
add_column :dossier_operation_logs, :digest, :text
|
||||||
|
add_index :dossier_operation_logs, :keep_until
|
||||||
|
end
|
||||||
|
end
|
|
@ -10,7 +10,7 @@
|
||||||
#
|
#
|
||||||
# It's strongly recommended that you check this file into your version control system.
|
# It's strongly recommended that you check this file into your version control system.
|
||||||
|
|
||||||
ActiveRecord::Schema.define(version: 2019_03_27_102357) do
|
ActiveRecord::Schema.define(version: 2019_03_27_102360) do
|
||||||
|
|
||||||
# These are extensions that must be enabled in order to support this database
|
# These are extensions that must be enabled in order to support this database
|
||||||
enable_extension "plpgsql"
|
enable_extension "plpgsql"
|
||||||
|
@ -221,9 +221,13 @@ ActiveRecord::Schema.define(version: 2019_03_27_102357) do
|
||||||
t.datetime "updated_at", null: false
|
t.datetime "updated_at", null: false
|
||||||
t.boolean "automatic_operation", default: false, null: false
|
t.boolean "automatic_operation", default: false, null: false
|
||||||
t.bigint "administration_id"
|
t.bigint "administration_id"
|
||||||
|
t.datetime "keep_until"
|
||||||
|
t.datetime "executed_at"
|
||||||
|
t.text "digest"
|
||||||
t.index ["administration_id"], name: "index_dossier_operation_logs_on_administration_id"
|
t.index ["administration_id"], name: "index_dossier_operation_logs_on_administration_id"
|
||||||
t.index ["dossier_id"], name: "index_dossier_operation_logs_on_dossier_id"
|
t.index ["dossier_id"], name: "index_dossier_operation_logs_on_dossier_id"
|
||||||
t.index ["gestionnaire_id"], name: "index_dossier_operation_logs_on_gestionnaire_id"
|
t.index ["gestionnaire_id"], name: "index_dossier_operation_logs_on_gestionnaire_id"
|
||||||
|
t.index ["keep_until"], name: "index_dossier_operation_logs_on_keep_until"
|
||||||
end
|
end
|
||||||
|
|
||||||
create_table "dossiers", id: :serial, force: :cascade do |t|
|
create_table "dossiers", id: :serial, force: :cascade do |t|
|
||||||
|
|
|
@ -15,6 +15,7 @@
|
||||||
"debounce": "^1.2.0",
|
"debounce": "^1.2.0",
|
||||||
"dom4": "^2.1.4",
|
"dom4": "^2.1.4",
|
||||||
"highcharts": "^6.1.2",
|
"highcharts": "^6.1.2",
|
||||||
|
"intersection-observer": "^0.6.0",
|
||||||
"jquery": "^3.4.1",
|
"jquery": "^3.4.1",
|
||||||
"leaflet": "^1.4.0",
|
"leaflet": "^1.4.0",
|
||||||
"leaflet-freedraw": "^2.10.0",
|
"leaflet-freedraw": "^2.10.0",
|
||||||
|
@ -23,6 +24,7 @@
|
||||||
"ramda": "=0.24.1",
|
"ramda": "=0.24.1",
|
||||||
"react": "^16.8.6",
|
"react": "^16.8.6",
|
||||||
"react-dom": "^16.8.6",
|
"react-dom": "^16.8.6",
|
||||||
|
"react-intersection-observer": "^8.23.0",
|
||||||
"react-scroll-to-component": "^1.0.2",
|
"react-scroll-to-component": "^1.0.2",
|
||||||
"react-sortable-hoc": "^1.7.1",
|
"react-sortable-hoc": "^1.7.1",
|
||||||
"react_ujs": "^2.5.0",
|
"react_ujs": "^2.5.0",
|
||||||
|
|
|
@ -27,6 +27,7 @@ RSpec.describe AutoArchiveProcedureJob, type: :job do
|
||||||
let!(:dossier7) { create(:dossier, procedure: procedure_hier, state: Dossier.states.fetch(:refuse), archived: false) }
|
let!(:dossier7) { create(:dossier, procedure: procedure_hier, state: Dossier.states.fetch(:refuse), archived: false) }
|
||||||
let!(:dossier8) { create(:dossier, procedure: procedure_hier, state: Dossier.states.fetch(:sans_suite), archived: false) }
|
let!(:dossier8) { create(:dossier, procedure: procedure_hier, state: Dossier.states.fetch(:sans_suite), archived: false) }
|
||||||
let!(:dossier9) { create(:dossier, procedure: procedure_aujourdhui, state: Dossier.states.fetch(:en_construction), archived: false) }
|
let!(:dossier9) { create(:dossier, procedure: procedure_aujourdhui, state: Dossier.states.fetch(:en_construction), archived: false) }
|
||||||
|
let(:last_operation) { dossier2.dossier_operation_logs.last }
|
||||||
|
|
||||||
before do
|
before do
|
||||||
subject
|
subject
|
||||||
|
@ -40,7 +41,8 @@ RSpec.describe AutoArchiveProcedureJob, type: :job do
|
||||||
it {
|
it {
|
||||||
expect(dossier1.state).to eq Dossier.states.fetch(:brouillon)
|
expect(dossier1.state).to eq Dossier.states.fetch(:brouillon)
|
||||||
expect(dossier2.state).to eq Dossier.states.fetch(:en_instruction)
|
expect(dossier2.state).to eq Dossier.states.fetch(:en_instruction)
|
||||||
expect(dossier2.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[nil, 'passer_en_instruction', true]])
|
expect(last_operation.operation).to eq('passer_en_instruction')
|
||||||
|
expect(last_operation.automatic_operation?).to be_truthy
|
||||||
expect(dossier3.state).to eq Dossier.states.fetch(:en_instruction)
|
expect(dossier3.state).to eq Dossier.states.fetch(:en_instruction)
|
||||||
expect(dossier4.state).to eq Dossier.states.fetch(:en_instruction)
|
expect(dossier4.state).to eq Dossier.states.fetch(:en_instruction)
|
||||||
expect(dossier5.state).to eq Dossier.states.fetch(:en_instruction)
|
expect(dossier5.state).to eq Dossier.states.fetch(:en_instruction)
|
||||||
|
|
|
@ -31,11 +31,13 @@ RSpec.describe AutoReceiveDossiersForProcedureJob, type: :job do
|
||||||
context "with some dossiers" do
|
context "with some dossiers" do
|
||||||
context "en_construction" do
|
context "en_construction" do
|
||||||
let(:state) { Dossier.states.fetch(:en_instruction) }
|
let(:state) { Dossier.states.fetch(:en_instruction) }
|
||||||
|
let(:last_operation) { nouveau_dossier1.dossier_operation_logs.last }
|
||||||
|
|
||||||
it {
|
it {
|
||||||
expect(nouveau_dossier1.en_instruction?).to be true
|
expect(nouveau_dossier1.en_instruction?).to be true
|
||||||
expect(nouveau_dossier1.en_instruction_at).to eq(date)
|
expect(nouveau_dossier1.en_instruction_at).to eq(date)
|
||||||
expect(nouveau_dossier1.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[nil, 'passer_en_instruction', true]])
|
expect(last_operation.operation).to eq('passer_en_instruction')
|
||||||
|
expect(last_operation.automatic_operation?).to be_truthy
|
||||||
|
|
||||||
expect(nouveau_dossier2.en_instruction?).to be true
|
expect(nouveau_dossier2.en_instruction?).to be true
|
||||||
expect(nouveau_dossier2.en_instruction_at).to eq(date)
|
expect(nouveau_dossier2.en_instruction_at).to eq(date)
|
||||||
|
@ -50,13 +52,15 @@ RSpec.describe AutoReceiveDossiersForProcedureJob, type: :job do
|
||||||
|
|
||||||
context "accepte" do
|
context "accepte" do
|
||||||
let(:state) { Dossier.states.fetch(:accepte) }
|
let(:state) { Dossier.states.fetch(:accepte) }
|
||||||
|
let(:last_operation) { nouveau_dossier1.dossier_operation_logs.last }
|
||||||
|
|
||||||
it {
|
it {
|
||||||
expect(nouveau_dossier1.accepte?).to be true
|
expect(nouveau_dossier1.accepte?).to be true
|
||||||
expect(nouveau_dossier1.en_instruction_at).to eq(date)
|
expect(nouveau_dossier1.en_instruction_at).to eq(date)
|
||||||
expect(nouveau_dossier1.processed_at).to eq(date)
|
expect(nouveau_dossier1.processed_at).to eq(date)
|
||||||
expect(nouveau_dossier1.attestation).to be_present
|
expect(nouveau_dossier1.attestation).to be_present
|
||||||
expect(nouveau_dossier1.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[nil, 'accepter', true]])
|
expect(last_operation.operation).to eq('accepter')
|
||||||
|
expect(last_operation.automatic_operation?).to be_truthy
|
||||||
|
|
||||||
expect(nouveau_dossier2.accepte?).to be true
|
expect(nouveau_dossier2.accepte?).to be true
|
||||||
expect(nouveau_dossier2.en_instruction_at).to eq(date)
|
expect(nouveau_dossier2.en_instruction_at).to eq(date)
|
||||||
|
|
|
@ -764,6 +764,8 @@ describe Dossier do
|
||||||
|
|
||||||
describe '#accepter!' do
|
describe '#accepter!' do
|
||||||
let(:dossier) { create(:dossier) }
|
let(:dossier) { create(:dossier) }
|
||||||
|
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||||
|
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||||
let!(:gestionnaire) { create(:gestionnaire) }
|
let!(:gestionnaire) { create(:gestionnaire) }
|
||||||
let!(:now) { Time.zone.parse('01/01/2100') }
|
let!(:now) { Time.zone.parse('01/01/2100') }
|
||||||
let(:attestation) { Attestation.new }
|
let(:attestation) { Attestation.new }
|
||||||
|
@ -783,13 +785,18 @@ describe Dossier do
|
||||||
it { expect(dossier.en_instruction_at).to eq(now) }
|
it { expect(dossier.en_instruction_at).to eq(now) }
|
||||||
it { expect(dossier.processed_at).to eq(now) }
|
it { expect(dossier.processed_at).to eq(now) }
|
||||||
it { expect(dossier.state).to eq('accepte') }
|
it { expect(dossier.state).to eq('accepte') }
|
||||||
it { expect(dossier.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[gestionnaire.id, 'accepter', false]]) }
|
it { expect(last_operation.operation).to eq('accepter') }
|
||||||
|
it { expect(last_operation.automatic_operation?).to be_falsey }
|
||||||
|
it { expect(operation_serialized['operation']).to eq('accepter') }
|
||||||
|
it { expect(operation_serialized['dossier_id']).to eq(dossier.id) }
|
||||||
|
it { expect(operation_serialized['executed_at']).to eq(last_operation.executed_at.iso8601) }
|
||||||
it { expect(NotificationMailer).to have_received(:send_closed_notification).with(dossier) }
|
it { expect(NotificationMailer).to have_received(:send_closed_notification).with(dossier) }
|
||||||
it { expect(dossier.attestation).to eq(attestation) }
|
it { expect(dossier.attestation).to eq(attestation) }
|
||||||
end
|
end
|
||||||
|
|
||||||
describe '#accepter_automatiquement!' do
|
describe '#accepter_automatiquement!' do
|
||||||
let(:dossier) { create(:dossier) }
|
let(:dossier) { create(:dossier) }
|
||||||
|
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||||
let!(:now) { Time.zone.parse('01/01/2100') }
|
let!(:now) { Time.zone.parse('01/01/2100') }
|
||||||
let(:attestation) { Attestation.new }
|
let(:attestation) { Attestation.new }
|
||||||
|
|
||||||
|
@ -808,30 +815,43 @@ describe Dossier do
|
||||||
it { expect(dossier.en_instruction_at).to eq(now) }
|
it { expect(dossier.en_instruction_at).to eq(now) }
|
||||||
it { expect(dossier.processed_at).to eq(now) }
|
it { expect(dossier.processed_at).to eq(now) }
|
||||||
it { expect(dossier.state).to eq('accepte') }
|
it { expect(dossier.state).to eq('accepte') }
|
||||||
it { expect(dossier.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[nil, 'accepter', true]]) }
|
it { expect(last_operation.operation).to eq('accepter') }
|
||||||
|
it { expect(last_operation.automatic_operation?).to be_truthy }
|
||||||
it { expect(NotificationMailer).to have_received(:send_closed_notification).with(dossier) }
|
it { expect(NotificationMailer).to have_received(:send_closed_notification).with(dossier) }
|
||||||
it { expect(dossier.attestation).to eq(attestation) }
|
it { expect(dossier.attestation).to eq(attestation) }
|
||||||
end
|
end
|
||||||
|
|
||||||
describe '#passer_en_instruction!' do
|
describe '#passer_en_instruction!' do
|
||||||
let(:dossier) { create(:dossier) }
|
let(:dossier) { create(:dossier) }
|
||||||
|
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||||
|
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||||
let(:gestionnaire) { create(:gestionnaire) }
|
let(:gestionnaire) { create(:gestionnaire) }
|
||||||
|
|
||||||
before { dossier.passer_en_instruction!(gestionnaire) }
|
before { dossier.passer_en_instruction!(gestionnaire) }
|
||||||
|
|
||||||
it { expect(dossier.state).to eq('en_instruction') }
|
it { expect(dossier.state).to eq('en_instruction') }
|
||||||
it { expect(dossier.followers_gestionnaires).to include(gestionnaire) }
|
it { expect(dossier.followers_gestionnaires).to include(gestionnaire) }
|
||||||
it { expect(dossier.dossier_operation_logs.pluck(:gestionnaire_id, :operation)).to match([[gestionnaire.id, 'passer_en_instruction']]) }
|
it { expect(last_operation.operation).to eq('passer_en_instruction') }
|
||||||
|
it { expect(last_operation.automatic_operation?).to be_falsey }
|
||||||
|
it { expect(operation_serialized['operation']).to eq('passer_en_instruction') }
|
||||||
|
it { expect(operation_serialized['dossier_id']).to eq(dossier.id) }
|
||||||
|
it { expect(operation_serialized['executed_at']).to eq(last_operation.executed_at.iso8601) }
|
||||||
end
|
end
|
||||||
|
|
||||||
describe '#passer_automatiquement_en_instruction!' do
|
describe '#passer_automatiquement_en_instruction!' do
|
||||||
let(:dossier) { create(:dossier) }
|
let(:dossier) { create(:dossier) }
|
||||||
|
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||||
|
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||||
let(:gestionnaire) { create(:gestionnaire) }
|
let(:gestionnaire) { create(:gestionnaire) }
|
||||||
|
|
||||||
before { dossier.passer_automatiquement_en_instruction! }
|
before { dossier.passer_automatiquement_en_instruction! }
|
||||||
|
|
||||||
it { expect(dossier.followers_gestionnaires).not_to include(gestionnaire) }
|
it { expect(dossier.followers_gestionnaires).not_to include(gestionnaire) }
|
||||||
it { expect(dossier.dossier_operation_logs.pluck(:gestionnaire_id, :operation, :automatic_operation)).to match([[nil, 'passer_en_instruction', true]]) }
|
it { expect(last_operation.operation).to eq('passer_en_instruction') }
|
||||||
|
it { expect(last_operation.automatic_operation?).to be_truthy }
|
||||||
|
it { expect(operation_serialized['operation']).to eq('passer_en_instruction') }
|
||||||
|
it { expect(operation_serialized['dossier_id']).to eq(dossier.id) }
|
||||||
|
it { expect(operation_serialized['executed_at']).to eq(last_operation.executed_at.iso8601) }
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "#check_mandatory_champs" do
|
describe "#check_mandatory_champs" do
|
||||||
|
@ -934,6 +954,6 @@ describe Dossier do
|
||||||
|
|
||||||
it { expect(dossier.hidden_at).to eq(Time.zone.now) }
|
it { expect(dossier.hidden_at).to eq(Time.zone.now) }
|
||||||
it { expect(last_operation.operation).to eq('supprimer') }
|
it { expect(last_operation.operation).to eq('supprimer') }
|
||||||
it { expect(last_operation.administration).to eq(administration) }
|
it { expect(last_operation.automatic_operation?).to be_falsey }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
26
yarn.lock
26
yarn.lock
|
@ -688,6 +688,13 @@
|
||||||
"@babel/plugin-transform-react-jsx-self" "^7.0.0"
|
"@babel/plugin-transform-react-jsx-self" "^7.0.0"
|
||||||
"@babel/plugin-transform-react-jsx-source" "^7.0.0"
|
"@babel/plugin-transform-react-jsx-source" "^7.0.0"
|
||||||
|
|
||||||
|
"@babel/runtime@^7.0.0":
|
||||||
|
version "7.4.4"
|
||||||
|
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.4.4.tgz#dc2e34982eb236803aa27a07fea6857af1b9171d"
|
||||||
|
integrity sha512-w0+uT71b6Yi7i5SE0co4NioIpSYS6lLiXvCzWzGSKvpK5vdQtCbICHMj+gbAKAOtxiV6HsVh/MBdaF9EQ6faSg==
|
||||||
|
dependencies:
|
||||||
|
regenerator-runtime "^0.13.2"
|
||||||
|
|
||||||
"@babel/runtime@^7.2.0", "@babel/runtime@^7.3.4", "@babel/runtime@^7.4.2":
|
"@babel/runtime@^7.2.0", "@babel/runtime@^7.3.4", "@babel/runtime@^7.4.2":
|
||||||
version "7.4.3"
|
version "7.4.3"
|
||||||
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.4.3.tgz#79888e452034223ad9609187a0ad1fe0d2ad4bdc"
|
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.4.3.tgz#79888e452034223ad9609187a0ad1fe0d2ad4bdc"
|
||||||
|
@ -4166,9 +4173,14 @@ internal-ip@^4.2.0:
|
||||||
ipaddr.js "^1.9.0"
|
ipaddr.js "^1.9.0"
|
||||||
|
|
||||||
interpret@^1.1.0:
|
interpret@^1.1.0:
|
||||||
version "1.2.0"
|
version "1.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/interpret/-/interpret-1.2.0.tgz#d5061a6224be58e8083985f5014d844359576296"
|
resolved "https://registry.yarnpkg.com/interpret/-/interpret-1.1.0.tgz#7ed1b1410c6a0e0f78cf95d3b8440c63f78b8614"
|
||||||
integrity sha512-mT34yGKMNceBQUoVn7iCDKDntA7SC6gycMAWzGx1z/CMCTV7b2AAtXlo3nRyHZ1FelRkQbQjprHSYGwzLtkVbw==
|
integrity sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=
|
||||||
|
|
||||||
|
intersection-observer@^0.6.0:
|
||||||
|
version "0.6.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/intersection-observer/-/intersection-observer-0.6.0.tgz#d64aae04211b4cec051537168f5fa670a4acc770"
|
||||||
|
integrity sha512-WUVAqGJr08yh73XKe1JhylQ9BiBIytrkt8SH5Knu7Uy44ij5cICi6PbVLIbV/D2eIx9LJVkGBo9WF80R4VXJ+w==
|
||||||
|
|
||||||
invariant@^2.2.2, invariant@^2.2.4:
|
invariant@^2.2.2, invariant@^2.2.4:
|
||||||
version "2.2.4"
|
version "2.2.4"
|
||||||
|
@ -6737,6 +6749,14 @@ react-dom@^16.8.6:
|
||||||
prop-types "^15.6.2"
|
prop-types "^15.6.2"
|
||||||
scheduler "^0.13.6"
|
scheduler "^0.13.6"
|
||||||
|
|
||||||
|
react-intersection-observer@^8.23.0:
|
||||||
|
version "8.23.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/react-intersection-observer/-/react-intersection-observer-8.23.0.tgz#1533aaf39cc70300ff8ca37e6551d2d68a589cd0"
|
||||||
|
integrity sha512-kHXfxhGKvVDNkrvmh9CKCnAWvJBigyB7oSDzMXL54weFDwwI4WfTr58YauZ0RRPkGzoD/hYEuzfS1wipXn23fA==
|
||||||
|
dependencies:
|
||||||
|
"@babel/runtime" "^7.0.0"
|
||||||
|
invariant "^2.2.4"
|
||||||
|
|
||||||
react-is@^16.8.1:
|
react-is@^16.8.1:
|
||||||
version "16.8.6"
|
version "16.8.6"
|
||||||
resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.8.6.tgz#5bbc1e2d29141c9fbdfed456343fe2bc430a6a16"
|
resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.8.6.tgz#5bbc1e2d29141c9fbdfed456343fe2bc430a6a16"
|
||||||
|
|
Loading…
Reference in a new issue