feat(indépendant): ajoute le simulateur cessation d’activité

feat/simulateur_cessation_activité
Jalil Arfaoui 2024-08-07 00:59:07 +02:00
parent 94a949f9d4
commit 6a39e1fd2f
36 changed files with 615 additions and 267 deletions

View File

@ -68,6 +68,12 @@ entreprise . durée d'activité . années civiles:
depuis: date de création
unité: année civile
entreprise . date de radiation:
question: À quelle date comptez-vous déclarer la cessation dactivité ?
par défaut: période . fin d'année
description: La date de radiation est la date à laquelle lentreprise cessera son activité.
type: date
entreprise . chiffre d'affaires:
question: Quel est votre chiffre d'affaires envisagé ?
identifiant court: CA

View File

@ -12,8 +12,7 @@ import { Strong } from '@/design-system/typography'
import { H1, H4 } from '@/design-system/typography/heading'
import { Link } from '@/design-system/typography/link'
import { Body } from '@/design-system/typography/paragraphs'
import { useUrl } from '../ShareSimulationBanner'
import { useUrl } from '@/hooks/useUrl'
type SubmitError = {
message?: string

View File

@ -1,57 +1,36 @@
import { useContext } from 'react'
import { Trans, useTranslation } from 'react-i18next'
import { useSelector } from 'react-redux'
import { styled } from 'styled-components'
import { PopoverWithTrigger } from '@/design-system'
import { Button } from '@/design-system/buttons'
import { Emoji } from '@/design-system/emoji'
import { Grid, Spacing } from '@/design-system/layout'
import { useCurrentSimulatorData } from '@/hooks/useCurrentSimulatorData'
import {
companySituationSelector,
situationSelector,
targetUnitSelector,
} from '@/store/selectors/simulationSelectors'
import { useUrl } from '@/hooks/useUrl'
import { TrackingContext } from '../ATInternetTracking'
import { ConseillersEntreprisesButton } from '../ConseillersEntreprisesButton'
import { useParamsFromSituation } from '../utils/useSearchParamsSimulationSharing'
import { ShareSimulationPopup } from './ShareSimulationPopup'
export function useUrl() {
const language = useTranslation().i18n.language
const situation = {
...useSelector(situationSelector),
...useSelector(companySituationSelector),
}
const targetUnit = useSelector(targetUnitSelector)
const searchParams = useParamsFromSituation(situation, targetUnit)
const { currentSimulatorData } = useCurrentSimulatorData()
const { path = '' } = currentSimulatorData ?? {}
const siteUrl =
language === 'fr'
? import.meta.env.VITE_FR_BASE_URL
: import.meta.env.VITE_EN_BASE_URL
return siteUrl + path + '?' + searchParams.toString()
}
const ButtonLabel = styled.span`
margin-left: 1rem;
`
export interface CustomSimulationButton {
href: string
title: string
}
export default function ShareOrSaveSimulationBanner({
share,
print,
conseillersEntreprises,
customSimulationbutton,
}: {
share?: boolean
print?: boolean
conseillersEntreprises?: boolean
customSimulationbutton?: CustomSimulationButton
}) {
const { t } = useTranslation()
const tracker = useContext(TrackingContext)
@ -92,6 +71,14 @@ export default function ShareOrSaveSimulationBanner({
justifyContent: 'center',
}}
>
{customSimulationbutton && (
<Grid item xs={12} sm="auto">
<Button light size="XS" href={customSimulationbutton.href}>
{customSimulationbutton.title}
</Button>
</Grid>
)}
{share && (
<Grid item xs={12} sm="auto">
<PopoverWithTrigger

View File

@ -1,4 +1,4 @@
import { useContext } from 'react'
import React, { ReactNode, useContext } from 'react'
import { Trans } from 'react-i18next'
import { styled } from 'styled-components'
@ -13,10 +13,12 @@ import { EngineContext } from './utils/EngineContext'
type SimulateurWarningProps = {
simulateur: Exclude<keyof AbsoluteSitePaths['simulateurs'], 'index'>
informationsComplémentaires?: ReactNode
}
export default function SimulateurWarning({
simulateur,
informationsComplémentaires,
}: SimulateurWarningProps) {
const year = useContext(EngineContext)
.evaluate('date')
@ -57,6 +59,11 @@ export default function SimulateurWarning({
</StyledLi>
</Ul>
)}
{informationsComplémentaires && (
<Ul>
<StyledLi>{informationsComplémentaires}</StyledLi>
</Ul>
)}
{simulateur === 'profession-libérale' && (
<Ul>
<StyledLi>

View File

@ -5,9 +5,13 @@ import { useLocation } from 'react-router-dom'
import { styled } from 'styled-components'
import { ConversationProps } from '@/components/conversation/Conversation'
import ShareOrSaveSimulationBanner from '@/components/ShareSimulationBanner'
import ShareOrSaveSimulationBanner, {
CustomSimulationButton,
} from '@/components/ShareSimulationBanner'
import { PopoverWithTrigger } from '@/design-system'
import { Button } from '@/design-system/buttons'
import { Grid, Spacing } from '@/design-system/layout'
import { H3 } from '@/design-system/typography/heading'
import { Link } from '@/design-system/typography/link'
import {
companySituationSelector,
@ -27,6 +31,16 @@ export { Questions } from './Questions'
export { SimulationGoal } from './SimulationGoal'
export { SimulationGoals } from './SimulationGoals'
const StyledGrid = styled(Grid)`
width: 100%;
@media print {
max-width: initial;
flex-basis: initial;
flex-grow: 1;
margin: 0 1rem;
}
`
type SimulationProps = {
explanations?: React.ReactNode
results?: React.ReactNode
@ -37,18 +51,9 @@ type SimulationProps = {
customEndMessages?: ConversationProps['customEndMessages']
fullWidth?: boolean
id?: string
customSimulationbutton?: CustomSimulationButton
}
const StyledGrid = styled(Grid)`
width: 100%;
@media print {
max-width: initial;
flex-basis: initial;
flex-grow: 1;
margin: 0 1rem;
}
`
export default function Simulation({
explanations,
results,
@ -59,6 +64,7 @@ export default function Simulation({
hideDetails = false,
fullWidth,
id,
customSimulationbutton,
}: SimulationProps) {
const firstStepCompleted = useSelector(firstStepCompletedSelector)
const existingCompany = !!useSelector(companySituationSelector)[
@ -115,6 +121,21 @@ export default function Simulation({
)}
{firstStepCompleted && !hideDetails && (
<>
{customSimulationbutton && (
<>
<div>
<H3>
Avez-vous besoin de calculer les cotisations de l'année
précédente ?
</H3>
<Button size="MD" href={customSimulationbutton.href}>
{customSimulationbutton.title}
</Button>
</div>
<Spacing lg />
</>
)}
<ShareOrSaveSimulationBanner share print conseillersEntreprises />
<Spacing lg />
</>

View File

@ -1,9 +1,9 @@
import { Trans } from 'react-i18next'
import { useUrl } from '@/components/ShareSimulationBanner'
import { Message } from '@/design-system'
import { Link } from '@/design-system/typography/link'
import { Body } from '@/design-system/typography/paragraphs'
import { useUrl } from '@/hooks/useUrl'
export default function PrintExportRecover() {
return (

View File

@ -0,0 +1,27 @@
import { useSelector } from 'react-redux'
import { useParamsFromSituation } from '@/components/utils/useSearchParamsSimulationSharing'
import {
companySituationSelector,
situationSelector,
targetUnitSelector,
} from '@/store/selectors/simulationSelectors'
export const useSearchParamsForCurrentSituation = <
T extends boolean | undefined,
>(
asString: T
): T extends true ? string : object => {
const situation = {
...useSelector(situationSelector),
...useSelector(companySituationSelector),
}
const targetUnit = useSelector(targetUnitSelector)
const searchParams = useParamsFromSituation(situation, targetUnit)
return (asString ? searchParams.toString() : searchParams) as T extends true
? string
: object
}

View File

@ -0,0 +1,9 @@
import { useTranslation } from 'react-i18next'
export const useSiteUrl = () => {
const language = useTranslation().i18n.language
return language === 'fr'
? import.meta.env.VITE_FR_BASE_URL
: import.meta.env.VITE_EN_BASE_URL
}

View File

@ -0,0 +1,11 @@
import { useCurrentSimulatorData } from '@/hooks/useCurrentSimulatorData'
import { useSearchParamsForCurrentSituation } from '@/hooks/useSearchParamsForCurrentSituation'
import { useSiteUrl } from '@/hooks/useSiteUrl'
export function useUrl() {
const { currentSimulatorData } = useCurrentSimulatorData()
const { path = '' } = currentSimulatorData ?? {}
return useSiteUrl() + path + '?' + useSearchParamsForCurrentSituation(true)
}

View File

@ -4033,14 +4033,14 @@ dirigeant . indépendant . cotisations facultatives . plafond retraite compléme
dirigeant . indépendant . revenu professionnel:
description.en: >-
[automatic] Professional income is the manager's remuneration under the
self-employment scheme.
self-employed workers' scheme.
For companies that have opted for the **income tax**, this is the **taxable income**.
For companies that have opted for the **taxe sur les sociétés**, this is the manager's remuneration, plus non-deductible contributions.
description.fr: >-
Le revenu professionnel est la rémunération du dirigeant au régime des
indépendant.
indépendants.
Pour les entreprises qui ont opté pour l'**impôt sur le revenu**, il s'agit du **résultat fiscal**.
@ -4082,7 +4082,7 @@ dirigeant . indépendant . revenu professionnel:
Dans la réalité, comme les cotisations sont régularisées d'une année sur l'autre, ce calcul n'est jamais à faire (sauf exceptions). Mais nous avons choisi de l'implémenter pour fournir le résultat le plus proche sans avoir à demander le montant des cotisations provisionnelles payées l'année N-1.
résumé.en: "[automatic] executive compensation under the self-employed workers' scheme"
résumé.fr: rémunération du dirigeant au régime des indépendant
résumé.fr: rémunération du dirigeant au régime des indépendants
titre.en: '[automatic] professional income'
titre.fr: revenu professionnel
dirigeant . indépendant . revenus étrangers:
@ -4526,47 +4526,6 @@ entreprise . TVA:
entreprise . TVA . franchise de TVA:
titre.en: '[automatic] VAT exemption'
titre.fr: franchise de TVA
entreprise . TVA . franchise de TVA . notification:
description.en: >
[automatic] The VAT exemption is a device that exempts companies from the
declaration and payment of
declaration and payment of VAT. It applies below a threshold of
annual turnover depending on the activity.
The professional who falls under this system invoices his services or sales without tax, and cannot
and cannot deduct VAT from their purchases.
description.fr: |
La franchise de TVA est un dispositif qui exonère les entreprises de la
déclaration et du paiement de la TVA. Il s'applique en dessous d'un seuil de
chiffre d'affaire annuel dépendant de l'activité.
Le professionnel qui relève de ce dispositif facture ses prestations ou ses
ventes en hors taxe, et ne peut pas déduire la TVA de ses achats.
note.en: >
[automatic] We take into account here the increased thresholds (which apply
if the "reduced" threshold has not been exceeded in year `n - 2`)
note.fr: >
On prend compte ici des seuils majorés (qui s'appliquent si le seuil
"minoré" n'a pas été dépassé en année `n - 2`)
résumé.en: |
[automatic] You are below the VAT declaration threshold.
résumé.fr: |
Vous êtes en dessous du seuil de déclaration de TVA.
titre.en: '[automatic] notification'
titre.fr: notification
entreprise . TVA . franchise de TVA . seuil service:
titre.en: '[automatic] threshold service'
titre.fr: seuil service
entreprise . TVA . franchise de TVA . seuil vente:
titre.en: '[automatic] sales threshold'
titre.fr: seuil vente
entreprise . TVA . franchise de TVA . seuils dépassés:
titre.en: '[automatic] thresholds exceeded'
titre.fr: seuils dépassés
entreprise . activité:
titre.en: '[automatic] activity'
titre.fr: activité
@ -5775,6 +5734,22 @@ entreprise . coût formalités . création:
résumé.fr: Tous les frais liés à l'enregistrement (greffe, annonces, chambres)
titre.en: '[automatic] Total creation costs'
titre.fr: Total des coûts de création
entreprise . créée cette année:
description.en: '[automatic] Was the company created in the year of the simulation?'
description.fr: L'entreprise a-t-elle été créée l'année de la simulation ?
titre.en: '[automatic] Company created this year'
titre.fr: Entreprise créée cette année
entreprise . date de cessation:
description.en:
'[automatic] The cessation date is the date on which the company
will cease trading.'
description.fr:
La date de cessation est la date à laquelle lentreprise cessera
son activité.
question.en: '[automatic] When do you plan to declare your cessation of activity?'
question.fr: À quelle date comptez-vous déclarer la cessation dactivité ?
titre.en: '[automatic] termination date'
titre.fr: date de cessation
entreprise . date de création:
description.en: >
[automatic] The date of commencement of activity (or date of creation) is
@ -5841,6 +5816,9 @@ entreprise . durée d'activité . en fin d'année:
entreprise . durée d'activité . trimestres civils:
titre.en: '[automatic] Number of calendar quarters covered'
titre.fr: Nombre de trimestres civils couverts
entreprise . durée d'activité cette année:
titre.en: '[automatic] duration of activity this year'
titre.fr: durée d'activité cette année
entreprise . exercice:
avec:
date trop ancienne:
@ -6120,6 +6098,23 @@ entreprise . imposition . régime . réel simplifié:
entreprise . nom:
titre.en: '[automatic] name'
titre.fr: nom
entreprise . prorata temporis:
description.en: |
[automatic] Percentage of the company's fiscal year in progress
description.fr: |
Pourcentage d'exercice de l'entreprise sur l'année en cours
titre.en: '[automatic] prorata temporis'
titre.fr: prorata temporis
entreprise . radiée:
description.en: '[automatic] Will the company be deregistered in the year of the simulation?'
description.fr: L'entreprise sera-t-elle radiée l'année de la simulation ?
titre.en: '[automatic] Delisted company'
titre.fr: Entreprise radiée
entreprise . radiée cette année:
description.en: '[automatic] Will the company be deregistered in the year of the simulation?'
description.fr: L'entreprise sera-t-elle radiée l'année de la simulation ?
titre.en: '[automatic] Company written off this year'
titre.fr: Entreprise radiée cette année
entreprise . résultat fiscal:
titre.en: '[automatic] tax result'
titre.fr: résultat fiscal
@ -7554,6 +7549,9 @@ protection sociale . transport:
période:
titre.en: period
titre.fr: période
période . durée depuis le début d'année:
titre.en: '[automatic] year-to-date'
titre.fr: durée depuis le début d'année
période . début d'année:
titre.en: start of year
titre.fr: début d'année

View File

@ -69,6 +69,7 @@ Charger plus de résultats: Load more results
Charges: Charges
Chiffre d'affaires: Sales figures
Chiffre d'affaires estimé: Estimated sales
Chiffre d'affaires pour l'année de cessation: Sales for the year of cessation
Comment ça marche ? Voir la page explicative sur la page du dépôt github, nouvelle fenêtre:
How does it work? See the explanatory page on the github repository page, new
window
@ -263,7 +264,7 @@ Retour à la création: Back to creation
Retour à mon activité: Back to my activity
Retraite complémentaire: Supplementary pension
Retraite de base: Basic pension
Retrouver ma simulation, charger les données de ma précédente simulation.: Retrieve my simulation, load data from my previous simulation.
Retrouver ma précédente simulation, charger les données de ma précédente simulation.: Find my previous simulation, load data from my previous simulation.
Revenu (incluant les dépenses liées à l'activité): Income (including activity-related expenses)
Revenu après impôt: After-tax income
Revenu avant impôt: Income before tax
@ -275,6 +276,7 @@ Régime d'imposition: Taxation system
Réinitialiser: Reset
Réinitialiser la situation enregistrée: Reset registered situation
Rémunération brute: Gross remuneration
Rémunération totale pour l'année de cessation: Total compensation for the year of termination
Répartition du chiffre d'affaires: Sales breakdown
Répondez à quelques questions additionnelles afin de préciser votre résultat.: Answer a few additional questions to clarify your result.
Résultat fiscal: Taxable income
@ -311,6 +313,7 @@ Tableau indiquant le nombre de visites par {{period}}.: Table showing the number
Tableau présentant le nombre de visites par simulateur et par mois.: Table showing the number of visits per simulator per month.
Titres-restaurant: Meal vouchers
Total des cotisations et contributions: Total contributions
Total des cotisations à devoir pour l'année de cessation d'activité: Total contributions due for the year of cessation of activity
"Tous les ans, selon votre rémunération, <2>vous gagnez des points qui constituent votre pension de retraite complémentaire</2>. En fin de carrière, vos points sont transformés en <5>un montant qui sajoute chaque mois à votre retraite de base</5>. Cette valeur se calcule sur le long terme. Par exemple, au bout de 10 ans, vous auriez droit à :":
"Every year, depending on how much you earn, <2>you earn points that make up
your supplementary pension</2>. At the end of your career, your points are
@ -353,6 +356,7 @@ Voir ma situation: See my situation
Voir ma situation, accéder à la page de gestion de mon entreprise: View my situation, access my company management page
Vos attentes ne sont pas remplies: Your expectations are not met
Vos charges estimées: Your estimated expenses
Vos cotisations pour lannée précédente: Your contributions for the previous year
Vos droits pour la retraite: Your pension rights
Vos prestations santé: Your health benefits
Vos revenus: Your income
@ -1235,6 +1239,16 @@ pages:
title: "Lawyer: income simulator"
shortname: Lawyer
title: Income simulator for self-employed lawyers
cessation-activité:
meta:
description: Estimate your contributions for the year in which you cease
self-employed activity.
ogDescription: Estimate your contributions for the year in which you cease
self-employed activity.
ogTitle: "Self-employed : Estimated contributions for the year of cessation"
titre: "Self-employed : Estimated contributions for the year of cessation"
shortname: Cessation of activity
title: "Self-employed : Estimated contributions for the year of cessation"
chirurgien-dentiste:
meta:
description: Calculation of net income after contributions based on total income.

View File

@ -74,6 +74,7 @@ Charger plus de résultats: Charger plus de résultats
Charges: Charges
Chiffre d'affaires: Chiffre d'affaires
Chiffre d'affaires estimé: Chiffre d'affaires estimé
Chiffre d'affaires pour l'année de cessation: Chiffre d'affaires pour l'année de cessation
Comment ça marche ? Voir la page explicative sur la page du dépôt github, nouvelle fenêtre:
Comment ça marche ? Voir la page explicative sur la page du dépôt github,
nouvelle fenêtre
@ -278,7 +279,9 @@ Retour à la création: Retour à la création
Retour à mon activité: Retour à mon activité
Retraite complémentaire: Retraite complémentaire
Retraite de base: Retraite de base
Retrouver ma simulation, charger les données de ma précédente simulation.: Retrouver ma simulation, charger les données de ma précédente simulation.
Retrouver ma précédente simulation, charger les données de ma précédente simulation.:
Retrouver ma précédente simulation, charger les données de ma précédente
simulation.
Revenu (incluant les dépenses liées à l'activité): Revenu (incluant les dépenses liées à l'activité)
Revenu après impôt: Revenu après impôt
Revenu avant impôt: Revenu avant impôt
@ -290,6 +293,7 @@ Régime d'imposition: Régime d'imposition
Réinitialiser: Réinitialiser
Réinitialiser la situation enregistrée: Réinitialiser la situation enregistrée
Rémunération brute: Rémunération brute
Rémunération totale pour l'année de cessation: Rémunération totale pour l'année de cessation
Répartition du chiffre d'affaires: Répartition du chiffre d'affaires
Répondez à quelques questions additionnelles afin de préciser votre résultat.: Répondez à quelques questions additionnelles afin de préciser votre résultat.
Résultat fiscal: Résultat fiscal
@ -327,6 +331,7 @@ Tableau indiquant le nombre de visites par {{period}}.: Tableau indiquant le nom
Tableau présentant le nombre de visites par simulateur et par mois.: Tableau présentant le nombre de visites par simulateur et par mois.
Titres-restaurant: Titres-restaurant
Total des cotisations et contributions: Total des cotisations et contributions
Total des cotisations à devoir pour l'année de cessation d'activité: Total des cotisations à devoir pour l'année de cessation d'activité
"Tous les ans, selon votre rémunération, <2>vous gagnez des points qui constituent votre pension de retraite complémentaire</2>. En fin de carrière, vos points sont transformés en <5>un montant qui sajoute chaque mois à votre retraite de base</5>. Cette valeur se calcule sur le long terme. Par exemple, au bout de 10 ans, vous auriez droit à :":
"Tous les ans, selon votre rémunération, <2>vous gagnez des points qui
constituent votre pension de retraite complémentaire</2>. En fin de carrière,
@ -370,6 +375,7 @@ Voir ma situation: Voir ma situation
Voir ma situation, accéder à la page de gestion de mon entreprise: Voir ma situation, accéder à la page de gestion de mon entreprise
Vos attentes ne sont pas remplies: Vos attentes ne sont pas remplies
Vos charges estimées: Vos charges estimées
Vos cotisations pour lannée précédente: Vos cotisations pour lannée précédente
Vos droits pour la retraite: Vos droits pour la retraite
Vos prestations santé: Vos prestations santé
Vos revenus: Vos revenus
@ -1311,6 +1317,16 @@ pages:
title: "Avocat : simulateur de revenus"
shortname: Avocat
title: Simulateur de revenus pour avocat en libéral
cessation-activité:
meta:
description: Estimez vos cotisations de l'année de cessation de votre activité
en tant quindépendant.
ogDescription: Estimez vos cotisations de l'année de cessation de votre activité
en tant quindépendant.
ogTitle: "Indépendants : Estimation des cotisations pour l'année de cessation"
titre: "Indépendants : Estimation des cotisations pour l'année de cessation"
shortname: Cessation dactivité
title: "Indépendants : Estimation des cotisations pour l'année de cessation"
chirurgien-dentiste:
meta:
description: Calcul du revenu net après cotisations à partir du total des recettes.

View File

@ -160,7 +160,6 @@ export default function SimulateursEtAssistants() {
<SimulateurCard {...simulators.is} role="listitem" />
<SimulateurCard {...simulators.dividendes} role="listitem" />
<SimulateurCard {...simulators['demande-mobilité']} role="listitem" />
<SimulateurCard
{...simulators['coût-création-entreprise']}
role="listitem"
@ -169,6 +168,12 @@ export default function SimulateursEtAssistants() {
{...simulators['recherche-code-ape']}
role="listitem"
/>
<SimulateurCard
{...simulators['cessation-activité']}
role="listitem"
/>
<SimulateurCard {...simulators['demande-mobilité']} role="listitem" />
</Grid>
</section>
<section>

View File

@ -10,6 +10,7 @@ import { artisteAuteurConfig } from '../simulateurs/artiste-auteur/config'
import { autoEntrepreneurConfig } from '../simulateurs/auto-entrepreneur/config'
import { auxiliaireMédicalConfig } from '../simulateurs/auxiliaire-médical/config'
import { avocatConfig } from '../simulateurs/avocat/config'
import { cessationActivitéConfig } from '../simulateurs/cessation-activité/config'
import { chirurgienDentisteConfig } from '../simulateurs/chirurgien-dentiste/config'
import { chômagePartielConfig } from '../simulateurs/chômage-partiel/config'
import { cipavConfig } from '../simulateurs/cipav/config'
@ -63,6 +64,7 @@ const getMetadataSrc = (params: SimulatorsDataParams) => {
...impôtSociétéConfig(params),
...cipavConfig(params),
...réductionGénéraleConfig(params),
...cessationActivitéConfig(params),
// assistants:
...choixStatutJuridiqueConfig(params),

View File

@ -2,11 +2,9 @@ import { ImmutableType } from '@/types/utils'
import { PageConfig } from './types'
// Replace type by commented line when we upgrade to typescript v5:
export function config<
// const Base extends ImmutableType<PageConfig>
Base extends ImmutableType<PageConfig>,
>(base: ImmutableType<PageConfig> & Base) {
export function config<Base extends ImmutableType<PageConfig>>(
base: ImmutableType<PageConfig> & Base
) {
return {
[base.id]: base,
} as ImmutableType<{ [k in Base['id']]: Base }>

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configAuxiliaire } from '../profession-libérale/simulationConfig'
export function auxiliaireMédicalConfig({

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configAvocat } from '../profession-libérale/simulationConfig'
export function avocatConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -0,0 +1,47 @@
import { useTranslation } from 'react-i18next'
import { useSelector } from 'react-redux'
import SimulateurWarning from '@/components/SimulateurWarning'
import Simulation from '@/components/Simulation'
import { useParamsFromSituation } from '@/components/utils/useSearchParamsSimulationSharing'
import useSimulatorsData from '@/hooks/useSimulatorsData'
import { useSiteUrl } from '@/hooks/useSiteUrl'
import { CessationActivitéGoals } from '@/pages/simulateurs/cessation-activité/Goals'
import {
companySituationSelector,
situationSelector,
targetUnitSelector,
} from '@/store/selectors/simulationSelectors'
import { omit } from '@/utils'
export const CessationActivitéSimulation = () => {
const situation = {
...useSelector(situationSelector),
...useSelector(companySituationSelector),
}
const targetUnit = useSelector(targetUnitSelector)
const filteredSituation = omit(situation, 'entreprise . date de radiation')
const searchParams = useParamsFromSituation(filteredSituation, targetUnit)
const path = useSimulatorsData().indépendant.path
const lien = useSiteUrl() + path + '?' + searchParams.toString()
const { t } = useTranslation()
return (
<Simulation
customSimulationbutton={{
href: lien,
title: t('Vos cotisations pour lannée précédente'),
}}
>
<SimulateurWarning
simulateur="cessation-activité"
informationsComplémentaires={<>Warning</>}
/>
<CessationActivitéGoals />
</Simulation>
)
}

View File

@ -0,0 +1,60 @@
import { useTranslation } from 'react-i18next'
import ChiffreAffairesActivitéMixte from '@/components/ChiffreAffairesActivitéMixte'
import { Condition } from '@/components/EngineValue/Condition'
import { SimulationGoal, SimulationGoals } from '@/components/Simulation'
import { CessationActivitéToggles } from '@/pages/simulateurs/cessation-activité/Toggles'
export const CessationActivitéGoals = () => {
const { t } = useTranslation()
return (
<SimulationGoals
legend="Vos revenus dactivité lannée de cessation"
toggles={<CessationActivitéToggles />}
>
<Condition expression="entreprise . imposition = 'IR'">
<Condition expression="entreprise . imposition . régime . micro-entreprise = non">
<SimulationGoal
appear={false}
dottedName="entreprise . chiffre d'affaires"
label={t("Chiffre d'affaires pour l'année de cessation")}
/>
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<ChiffreAffairesActivitéMixte dottedName="entreprise . chiffre d'affaires" />
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise != oui">
<SimulationGoal
small
appear={false}
dottedName="entreprise . charges"
/>
</Condition>
</Condition>
<Condition expression="entreprise . imposition = 'IS'">
<SimulationGoal
appear={false}
dottedName="dirigeant . rémunération . totale"
label={t("Rémunération totale pour l'année de cessation")}
/>
</Condition>
<SimulationGoal
small
editable={false}
dottedName="dirigeant . indépendant . cotisations et contributions"
label={t(
"Total des cotisations à devoir pour l'année de cessation d'activité"
)}
/>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<SimulationGoal
small
appear={false}
dottedName="entreprise . charges"
/>
</Condition>
</SimulationGoals>
)
}

View File

@ -0,0 +1,70 @@
import { DottedName } from 'modele-social'
import { useDispatch } from 'react-redux'
import { DefaultValue } from '@/components/conversation/DefaultValue'
import { ExplicableRule } from '@/components/conversation/Explicable'
import RuleInput from '@/components/conversation/RuleInput'
import { useEngine } from '@/components/utils/EngineContext'
import { H3 } from '@/design-system/typography/heading'
import { SimpleRuleEvaluation } from '@/domaine/engine/SimpleRuleEvaluation'
import { ajusteLaSituation } from '@/store/actions/actions'
import { evaluateQuestion } from '@/utils/publicodes'
export const CessationActivitéToggles = () => {
const dispatch = useDispatch()
const engine = useEngine()
return (
<div
style={{
flexShrink: 0,
flexBasis: '100%',
display: 'flex',
flexDirection: 'column',
justifyContent: 'space-between',
}}
>
<div
style={{
display: 'flex',
flexDirection: 'column',
alignItems: 'start',
}}
>
<H3 id="questionHeader" as="h2">
{evaluateQuestion(
engine,
engine.getRule('entreprise . date de radiation')
)}
<ExplicableRule light dottedName={'entreprise . date de radiation'} />
</H3>
<RuleInput
dottedName="entreprise . date de radiation"
onChange={(date) => {
dispatch(
ajusteLaSituation({
'entreprise . date de radiation': date,
} as Record<DottedName, SimpleRuleEvaluation>)
)
}}
/>
<DefaultValue dottedName={'entreprise . date de radiation'} />
</div>
<RuleInput
inputType="toggle"
hideDefaultValue
missing={false}
dottedName="entreprise . imposition"
onChange={(imposition) => {
dispatch(
ajusteLaSituation({
'entreprise . imposition': imposition,
} as Record<DottedName, SimpleRuleEvaluation>)
)
}}
/>
</div>
)
}

View File

@ -0,0 +1,48 @@
import { SimulatorsDataParams } from '@/pages/simulateurs/_configs/types'
import { CessationActivitéSimulation } from '@/pages/simulateurs/cessation-activité/CessationActivité'
import { configCessationActivité } from '@/pages/simulateurs/cessation-activité/simulationConfig'
import { config } from '../_configs/config'
export function cessationActivitéConfig({
t,
sitePaths,
}: SimulatorsDataParams) {
return config({
id: 'cessation-activité',
tracking: 'cessation_activité',
icône: '📦',
iframePath: 'simulateur-cessation-activité',
pathId: 'simulateurs.cessation-activité',
shortName: t(
'pages.simulateurs.cessation-activité.shortname',
'Cessation dactivité'
),
title: t(
'pages.simulateurs.cessation-activité.title',
"Indépendants : Cotisations pour l'année de cessation"
),
meta: {
description: t(
'pages.simulateurs.cessation-activité.meta.description',
"Estimez vos cotisations de l'année de cessation de votre activité en tant quindépendant."
),
ogDescription: t(
'pages.simulateurs.cessation-activité.meta.ogDescription',
"Estimez vos cotisations de l'année de cessation de votre activité en tant quindépendant."
),
ogTitle: t(
'pages.simulateurs.cessation-activité.meta.ogTitle',
"Indépendants : Cotisations pour l'année de cessation"
),
title: t(
'pages.simulateurs.cessation-activité.meta.titre',
"Indépendants : Cotisations pour l'année de cessation"
),
},
nextSteps: ['indépendant'],
path: sitePaths.simulateurs['cessation-activité'],
simulation: configCessationActivité,
component: CessationActivitéSimulation,
} as const)
}

View File

@ -0,0 +1,7 @@
import { SimulationConfig } from '@/pages/simulateurs/_configs/types'
import { configIndépendant } from '@/pages/simulateurs/indépendant/simulationConfig'
export const configCessationActivité: SimulationConfig = {
...configIndépendant,
'unité par défaut': '€/an',
}

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configDentiste } from '../profession-libérale/simulationConfig'
export function chirurgienDentisteConfig({

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import cipavSimulationConfig from './simulationConfig'
export function cipavConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -1,10 +1,9 @@
import { EntrepriseIndividuelle } from '@/pages/simulateurs/indépendant/EntrepriseIndividuelle'
import { SeoExplanationsEI } from '@/pages/simulateurs/indépendant/SeoExplanationsEI'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import AutoEntrepreneurPreview from '../_images/AutoEntrepreneurPreview.png'
import {
EntrepriseIndividuelle,
SeoExplanationsEI,
} from '../indépendant/Indépendant'
import { configEntrepriseIndividuelle } from '../indépendant/simulationConfig'
export function entrepriseIndividuelleConfig({

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configExpertComptable } from '../profession-libérale/simulationConfig'
export function expertComptableConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -0,0 +1,17 @@
import { SelectSimulationYear } from '@/components/SelectSimulationYear'
import SimulateurWarning from '@/components/SimulateurWarning'
import Simulation from '@/components/Simulation'
import IndépendantExplanation from '@/components/simulationExplanation/IndépendantExplanation'
import { IndépendantSimulationGoals } from '@/pages/simulateurs/indépendant/Goals'
export const EntrepriseIndividuelle = () => (
<>
<Simulation
explanations={<IndépendantExplanation />}
afterQuestionsSlot={<SelectSimulationYear />}
>
<SimulateurWarning simulateur="entreprise-individuelle" />
<IndépendantSimulationGoals legend="Vos revenus d'entreprise individuelle" />
</Simulation>
</>
)

View File

@ -0,0 +1,53 @@
import ChiffreAffairesActivitéMixte from '@/components/ChiffreAffairesActivitéMixte'
import { Condition } from '@/components/EngineValue/Condition'
import PeriodSwitch from '@/components/PeriodSwitch'
import { SimulationGoal, SimulationGoals } from '@/components/Simulation'
export const IndépendantSimulationGoals = ({
toggles = <PeriodSwitch />,
legend,
}: {
toggles?: React.ReactNode
legend: string
}) => (
<SimulationGoals toggles={toggles} legend={legend}>
<Condition expression="entreprise . imposition = 'IR'">
<Condition expression="entreprise . imposition . régime . micro-entreprise = non">
<SimulationGoal
appear={false}
dottedName="entreprise . chiffre d'affaires"
/>
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<ChiffreAffairesActivitéMixte dottedName="entreprise . chiffre d'affaires" />
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise != oui">
<SimulationGoal
small
appear={false}
dottedName="entreprise . charges"
/>
</Condition>
</Condition>
<Condition expression="entreprise . imposition = 'IS'">
<SimulationGoal
appear={false}
dottedName="dirigeant . rémunération . totale"
/>
</Condition>
<SimulationGoal
small
editable={false}
dottedName="dirigeant . indépendant . cotisations et contributions"
/>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<SimulationGoal small appear={false} dottedName="entreprise . charges" />
</Condition>
<SimulationGoal dottedName="dirigeant . rémunération . net" />
<Condition expression="impôt . montant > 0">
<SimulationGoal small editable={false} dottedName="impôt . montant" />
</Condition>
<SimulationGoal dottedName="dirigeant . rémunération . net . après impôt" />
</SimulationGoals>
)

View File

@ -1,19 +1,14 @@
import { useDispatch } from 'react-redux'
import { DottedName } from 'modele-social'
import { Trans } from 'react-i18next'
import { useDispatch } from 'react-redux'
import ChiffreAffairesActivitéMixte from '@/components/ChiffreAffairesActivitéMixte'
import RuleInput from '@/components/conversation/RuleInput'
import { Condition } from '@/components/EngineValue/Condition'
import PeriodSwitch from '@/components/PeriodSwitch'
import RuleLink from '@/components/RuleLink'
import { SelectSimulationYear } from '@/components/SelectSimulationYear'
import SimulateurWarning from '@/components/SimulateurWarning'
import Simulation, {
SimulationGoal,
SimulationGoals,
} from '@/components/Simulation'
import Simulation from '@/components/Simulation'
import IndépendantExplanation from '@/components/simulationExplanation/IndépendantExplanation'
import { IndépendantSimulationGoals } from '@/pages/simulateurs/indépendant/Goals'
import { Message } from '@/design-system'
import { Emoji } from '@/design-system/emoji'
import { H2 } from '@/design-system/typography/heading'
@ -21,101 +16,6 @@ import { Body } from '@/design-system/typography/paragraphs'
import { SimpleRuleEvaluation } from '@/domaine/engine/SimpleRuleEvaluation'
import { ajusteLaSituation } from '@/store/actions/actions'
export function IndépendantPLSimulation() {
return (
<>
<Simulation
explanations={<IndépendantExplanation />}
afterQuestionsSlot={<SelectSimulationYear />}
>
<SimulateurWarning simulateur="profession-libérale" />
<IndépendantSimulationGoals legend="Vos revenus de profession libérale" />
</Simulation>
</>
)
}
export function EntrepriseIndividuelle() {
return (
<>
<Simulation
explanations={<IndépendantExplanation />}
afterQuestionsSlot={<SelectSimulationYear />}
>
<SimulateurWarning simulateur="entreprise-individuelle" />
<IndépendantSimulationGoals legend="Vos revenus d'entreprise individuelle" />
</Simulation>
</>
)
}
export const SeoExplanationsEI = () => (
<Trans i18nKey="pages.simulateurs.ei.seo explanation">
<H2>
Comment calculer le revenu net d'un dirigeant d'entreprise individuelle
(EI) ?
</H2>
<Body>
Un dirigeant d'entreprise individuelle doit payer des cotisations et
contributions sociales à l'administration. Ces cotisations servent au
financement de la sécurité sociale, et ouvrent des droits notamment pour
la retraite et pour l'assurance maladie. Elles permettent également de
financer la formation professionnelle.
</Body>
<Body>
<Emoji emoji="👉" />{' '}
<RuleLink dottedName="dirigeant . indépendant . cotisations et contributions">
Voir le détail du calcul des cotisations
</RuleLink>
</Body>
<Body>
Il ne faut pas oublier de retrancher toutes les dépenses effectuées dans
le cadre de l'activité professionnelle (équipements, matières premières,
local, transport). Ces dernières sont déductibles du résultat de
l'entreprise, cela veut dire que vous ne payerez pas d'impôt ou de
cotisations sur leur montant (sauf si vous avez opté pour l'option
micro-fiscal).
</Body>
<Body>La formule de calcul complète est donc :</Body>
<Message
role="presentation"
mini
border={false}
style={{
width: 'fit-content',
}}
>
Revenu net = Chiffres d'affaires Dépenses professionnelles - Cotisations
sociales
</Message>
<H2>
Comment calculer les cotisations sociales d'une entreprise individuelle ?
</H2>
<Body>
Le dirigeant d'une entreprise individuelle paye des cotisations sociales,
proportionnelle au{' '}
<RuleLink dottedName="entreprise . résultat fiscal">
résultat fiscal
</RuleLink>{' '}
de l'entreprise. Leur montant varie également en fonction du type
d'activité (profession libérale, artisan, commerçants, etc), où des
éventuelles exonérations accordées (ACRE, ZFU, RSA, etc.).
</Body>
<Body>
{' '}
Comme le résultat d'une entreprise n'est connu qu'à la fin de l'exercice
comptable, le dirigeant paye des cotisations provisionnelles qui seront
ensuite régularisée une fois le revenu réel déclaré, l'année suivante.
</Body>
<Body>
Ce simulateur permet de calculer le montant exact des cotisations sociale
en partant d'un chiffre d'affaires ou d'un revenu net souhaité. Vous
pourrez préciser votre situation en répondant aux questions s'affichant en
dessous de la simulation.
</Body>
</Trans>
)
export default function IndépendantSimulation() {
const dispatch = useDispatch()
@ -151,58 +51,3 @@ export default function IndépendantSimulation() {
</>
)
}
function IndépendantSimulationGoals({
toggles = <PeriodSwitch />,
legend,
}: {
toggles?: React.ReactNode
legend: string
}) {
return (
<SimulationGoals toggles={toggles} legend={legend}>
<Condition expression="entreprise . imposition = 'IR'">
<Condition expression="entreprise . imposition . régime . micro-entreprise = non">
<SimulationGoal
appear={false}
dottedName="entreprise . chiffre d'affaires"
/>
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<ChiffreAffairesActivitéMixte dottedName="entreprise . chiffre d'affaires" />
</Condition>
<Condition expression="entreprise . imposition . régime . micro-entreprise != oui">
<SimulationGoal
small
appear={false}
dottedName="entreprise . charges"
/>
</Condition>
</Condition>
<Condition expression="entreprise . imposition = 'IS'">
<SimulationGoal
appear={false}
dottedName="dirigeant . rémunération . totale"
/>
</Condition>
<SimulationGoal
small
editable={false}
dottedName="dirigeant . indépendant . cotisations et contributions"
/>
<Condition expression="entreprise . imposition . régime . micro-entreprise">
<SimulationGoal
small
appear={false}
dottedName="entreprise . charges"
/>
</Condition>
<SimulationGoal dottedName="dirigeant . rémunération . net" />
<Condition expression="impôt . montant > 0">
<SimulationGoal small editable={false} dottedName="impôt . montant" />
</Condition>
<SimulationGoal dottedName="dirigeant . rémunération . net . après impôt" />
</SimulationGoals>
)
}

View File

@ -0,0 +1,17 @@
import { SelectSimulationYear } from '@/components/SelectSimulationYear'
import SimulateurWarning from '@/components/SimulateurWarning'
import Simulation from '@/components/Simulation'
import IndépendantExplanation from '@/components/simulationExplanation/IndépendantExplanation'
import { IndépendantSimulationGoals } from '@/pages/simulateurs/indépendant/Goals'
export const IndépendantPLSimulation = () => (
<>
<Simulation
explanations={<IndépendantExplanation />}
afterQuestionsSlot={<SelectSimulationYear />}
>
<SimulateurWarning simulateur="profession-libérale" />
<IndépendantSimulationGoals legend="Vos revenus de profession libérale" />
</Simulation>
</>
)

View File

@ -0,0 +1,74 @@
import { Trans } from 'react-i18next'
import RuleLink from '@/components/RuleLink'
import { Message } from '@/design-system'
import { Emoji } from '@/design-system/emoji'
import { H2 } from '@/design-system/typography/heading'
import { Body } from '@/design-system/typography/paragraphs'
export const SeoExplanationsEI = () => (
<Trans i18nKey="pages.simulateurs.ei.seo explanation">
<H2>
Comment calculer le revenu net d'un dirigeant d'entreprise individuelle
(EI) ?
</H2>
<Body>
Un dirigeant d'entreprise individuelle doit payer des cotisations et
contributions sociales à l'administration. Ces cotisations servent au
financement de la sécurité sociale, et ouvrent des droits notamment pour
la retraite et pour l'assurance maladie. Elles permettent également de
financer la formation professionnelle.
</Body>
<Body>
<Emoji emoji="👉" />{' '}
<RuleLink dottedName="dirigeant . indépendant . cotisations et contributions">
Voir le détail du calcul des cotisations
</RuleLink>
</Body>
<Body>
Il ne faut pas oublier de retrancher toutes les dépenses effectuées dans
le cadre de l'activité professionnelle (équipements, matières premières,
local, transport). Ces dernières sont déductibles du résultat de
l'entreprise, cela veut dire que vous ne payerez pas d'impôt ou de
cotisations sur leur montant (sauf si vous avez opté pour l'option
micro-fiscal).
</Body>
<Body>La formule de calcul complète est donc :</Body>
<Message
role="presentation"
mini
border={false}
style={{
width: 'fit-content',
}}
>
Revenu net = Chiffres d'affaires Dépenses professionnelles - Cotisations
sociales
</Message>
<H2>
Comment calculer les cotisations sociales d'une entreprise individuelle ?
</H2>
<Body>
Le dirigeant d'une entreprise individuelle paye des cotisations sociales,
proportionnelle au{' '}
<RuleLink dottedName="entreprise . résultat fiscal">
résultat fiscal
</RuleLink>{' '}
de l'entreprise. Leur montant varie également en fonction du type
d'activité (profession libérale, artisan, commerçants, etc), où des
éventuelles exonérations accordées (ACRE, ZFU, RSA, etc.).
</Body>
<Body>
{' '}
Comme le résultat d'une entreprise n'est connu qu'à la fin de l'exercice
comptable, le dirigeant paye des cotisations provisionnelles qui seront
ensuite régularisée une fois le revenu réel déclaré, l'année suivante.
</Body>
<Body>
Ce simulateur permet de calculer le montant exact des cotisations sociale
en partant d'un chiffre d'affaires ou d'un revenu net souhaité. Vous
pourrez préciser votre situation en répondant aux questions s'affichant en
dessous de la simulation.
</Body>
</Trans>
)

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configMédecin } from '../profession-libérale/simulationConfig'
export function médecinConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configPharmacien } from '../profession-libérale/simulationConfig'
export function pharmacienConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configProfessionLibérale } from './simulationConfig'
export function professionLibéraleConfig({

View File

@ -1,6 +1,7 @@
import { IndépendantPLSimulation } from '@/pages/simulateurs/indépendant/IndépendantPLSimulation'
import { config } from '../_configs/config'
import { SimulatorsDataParams } from '../_configs/types'
import { IndépendantPLSimulation } from '../indépendant/Indépendant'
import { configSageFemme } from '../profession-libérale/simulationConfig'
export function sageFemmeConfig({ t, sitePaths }: SimulatorsDataParams) {

View File

@ -73,6 +73,7 @@ const rawSitePathsFr = {
is: 'impot-societe',
dividendes: 'dividendes',
'réduction-générale': 'réduction-générale',
'cessation-activité': 'cessation-activité',
},
nouveautés: {
index: 'nouveautés',
@ -172,6 +173,7 @@ const rawSitePathsEn = {
is: 'corporate-tax',
dividendes: 'dividends',
'réduction-générale': 'réduction-générale',
'cessation-activité': 'cessation-of-activity',
},
nouveautés: {
index: 'news',