diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 8fe4e2a2a..f99cfbea4 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -18,7 +18,7 @@ A few things:
- 🙏🏻 Don't be afraid to push even if you aren't 100% happy with your code or [if it's still WIP](https://github.com/codegouvfr/react-dsfr/blob/1fdcf15cb085c67d37c31badf6ffa4725795ba0f/stories/Accordion.stories.tsx#L6).
- 📣 Let everyone know what component you are working on by [oppening an issue](https://github.com/codegouvfr/react-dsfr/issues).
- 📚 You can draw inspiration from [`dataesr/react-dsfr`](https://github.com/dataesr/react-dsfr/tree/master/src/components/interface) and the implementation of [france connect](https://github.com/france-connect/sources/tree/main/front/libs/dsfr).
-- 🔗 Use the component returned by `useLink()` instead of ``. [Example in the `` component](https://github.com/codegouvfr/react-dsfr/blob/bbaf4a81d78de08d6fdcb059a9f4cb8a78ce4d5a/src/Header.tsx#L84-L87). We want to [play nice with all routing libraries](https://react-dsfr.etalab.studio/integration-with-routing-libraries).
+- 🔗 Use the component returned by `getLink()` instead of ``. [Example in the `` component](https://github.com/codegouvfr/react-dsfr/blob/bbaf4a81d78de08d6fdcb059a9f4cb8a78ce4d5a/src/Header.tsx#L84-L87). We want to [play nice with all routing libraries](https://react-dsfr.etalab.studio/integration-with-routing-libraries).
- 🕹️ When it's relevant, try to enable components to be used either in controlled or uncontrolled mode. [Example with ](https://react-dsfr-components.etalab.studio/?path=/docs/components-tabs--default).
- 🌎 Avoid hard coding text in JSX, use [the i18n mechanism](https://react-dsfr.etalab.studio/i18n) instead. [Here is an example](https://github.com/codegouvfr/react-dsfr/blob/bbaf4a81d78de08d6fdcb059a9f4cb8a78ce4d5a/src/DarkModeSwitch.tsx#L162-L199). (Don't worry about providing translations other than French.)
- 🍳 If you have to arbitrate between ease of use and customisability I'd encourage you to favor ease of use. People that would need a greater level of customizability can always fall back to making their own wrapper from the reference documentation using [`fr.cx()`](https://react-dsfr.etalab.studio/cx).
diff --git a/package.json b/package.json
index 1201817a2..0a89e7d96 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@codegouvfr/react-dsfr",
- "version": "0.56.0",
+ "version": "0.57.0",
"description": "French State Design System React integration library",
"repository": {
"type": "git",
diff --git a/scripts/build/build.ts b/scripts/build/build.ts
index 8cc6f8b32..6e4985105 100644
--- a/scripts/build/build.ts
+++ b/scripts/build/build.ts
@@ -1,6 +1,6 @@
import { tsc } from "../tools/tsc";
import { getProjectRoot } from "../../src/bin/tools/getProjectRoot";
-import { join as pathJoin } from "path";
+import { join as pathJoin, basename as pathBasename } from "path";
import * as fs from "fs";
import { getPatchedRawCssCodeForCompatWithRemixIcon, collectIcons } from "./icons";
import { cssToTs } from "./cssToTs";
@@ -105,6 +105,22 @@ import { patchCssForMui } from "./patchCssForMui";
"doWatch": false
});
+ {
+ const assertSrcDirPath = pathJoin(projectRootDirPath, "src", "assets");
+
+ fs.cpSync(
+ assertSrcDirPath,
+ pathJoin(
+ projectRootDirPath,
+ JSON.parse(
+ fs.readFileSync(pathJoin(projectRootDirPath, "tsproject.json")).toString("utf8")
+ )["compilerOptions"]["outDir"],
+ pathBasename(assertSrcDirPath)
+ ),
+ { "recursive": true }
+ );
+ }
+
//NOTE: From here it's only for local linking, required for storybook and running integration apps.
if (!args.npm) {
fs.writeFileSync(
diff --git a/src/AgentConnectButton.tsx b/src/AgentConnectButton.tsx
new file mode 100644
index 000000000..3b33d8d01
--- /dev/null
+++ b/src/AgentConnectButton.tsx
@@ -0,0 +1,95 @@
+"use client";
+import React, { forwardRef, memo, useState, type CSSProperties } from "react";
+import { symToStr } from "tsafe/symToStr";
+import { createComponentI18nApi } from "./i18n";
+import { fr } from "./fr";
+import { assert, type Equals } from "tsafe/assert";
+import agentconnectBtnPrincipalSvgUrl from "./assets/agentconnect-btn-principal.svg";
+import agentconnectBtnPrincipalHoverSvgUrl from "./assets/agentconnect-btn-principal-hover.svg";
+import agentconnectBtnAlternatifSvgUrl from "./assets/agentconnect-btn-alternatif.svg";
+import agentconnectBtnAlternatifHoverSvgUrl from "./assets/agentconnect-btn-alternatif-hover.svg";
+import { useIsDark } from "./useIsDark";
+import { useColors } from "./useColors";
+import { getAssetUrl } from "./tools/getAssetUrl";
+
+export type AgentConnectButtonProps = {
+ className?: string;
+ redirectUrl: string;
+ style?: CSSProperties;
+};
+
+/** @see */
+export const AgentConnectButton = memo(
+ forwardRef((props, ref) => {
+ const { className, redirectUrl, style, ...rest } = props;
+
+ assert>();
+
+ const { t } = useTranslation();
+
+ const [isMouseHover, setIsMouseHover] = useState(false);
+
+ const { isDark } = useIsDark();
+ const theme = useColors();
+
+ return (
+