@dotcms/react 1.5.5-next.2245 → 1.5.5-next.2260

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -4,6 +4,7 @@ import { useContext, useMemo } from 'react';
4
4
  import { getContainersData, getContentletsInContainer, getDotContainerAttributes } from '@dotcms/uve/internal';
5
5
  import { ContainerNotFound, EmptyContainer } from './ContainerFallbacks.esm.js';
6
6
  import { DotCMSPageContext } from '../../contexts/DotCMSPageContext.esm.js';
7
+ import { useIsDevMode } from '../../hooks/useIsDevMode.esm.js';
7
8
  import { Contentlet } from '../Contentlet/Contentlet.esm.js';
8
9
 
9
10
  /**
@@ -31,6 +32,7 @@ function Container({
31
32
  const {
32
33
  pageAsset
33
34
  } = useContext(DotCMSPageContext);
35
+ const isDevMode = useIsDevMode();
34
36
  const containerData = useMemo(() => getContainersData(pageAsset, container), [pageAsset, container]);
35
37
  const contentlets = useMemo(() => getContentletsInContainer(pageAsset, container), [pageAsset, container]);
36
38
  if (!containerData) {
@@ -39,7 +41,8 @@ function Container({
39
41
  });
40
42
  }
41
43
  const isEmpty = contentlets.length === 0;
42
- const dotAttributes = getDotContainerAttributes(containerData);
44
+ // Container metadata is editor-only — strip it from live output.
45
+ const dotAttributes = isDevMode ? getDotContainerAttributes(containerData) : {};
43
46
  if (isEmpty) {
44
47
  return jsx(EmptyContainer, Object.assign({}, dotAttributes));
45
48
  }
@@ -39,7 +39,7 @@ const ContainerNotFound = ({
39
39
  *
40
40
  * Component to display when a container is empty.
41
41
  *
42
- * @param {DotContainerAttributes} dotAttributes
42
+ * @param {Partial<DotContainerAttributes>} dotAttributes
43
43
  * @return {*}
44
44
  */
45
45
  const EmptyContainer = dotAttributes => {
@@ -1,9 +1,10 @@
1
1
  "use client";
2
2
  import { jsx, Fragment } from 'react/jsx-runtime';
3
3
  import { useRef, useMemo, useContext } from 'react';
4
- import { getDotContentletAttributes, CUSTOM_NO_COMPONENT } from '@dotcms/uve/internal';
4
+ import { getDotContentletAttributes, getAnalyticsContentletAttributes, CUSTOM_NO_COMPONENT } from '@dotcms/uve/internal';
5
5
  import { DotCMSPageContext } from '../../contexts/DotCMSPageContext.esm.js';
6
6
  import { useCheckVisibleContent } from '../../hooks/useCheckVisibleContent.esm.js';
7
+ import { useIsAnalyticsActive } from '../../hooks/useIsAnalyticsActive.esm.js';
7
8
  import { useIsDevMode } from '../../hooks/useIsDevMode.esm.js';
8
9
  import { FallbackComponent } from '../FallbackComponent/FallbackComponent.esm.js';
9
10
 
@@ -34,14 +35,26 @@ function Contentlet({
34
35
  }) {
35
36
  const ref = useRef(null);
36
37
  const isDevMode = useIsDevMode();
38
+ const isAnalyticsActive = useIsAnalyticsActive();
37
39
  const haveContent = useCheckVisibleContent(ref);
38
40
  const style = useMemo(() => isDevMode ? {
39
41
  minHeight: haveContent ? undefined : '4rem'
40
42
  } : {}, [isDevMode, haveContent]);
41
- // UVE attributes - always applied
42
- const dotAttributes = useMemo(() => getDotContentletAttributes(contentlet, container), [contentlet, container]);
43
+ // In edit mode we emit the full set of editor metadata. In live mode we
44
+ // strip it to avoid leaking internal identifiers, keeping only the minimal
45
+ // set Analytics needs (and only while Analytics is active).
46
+ const dotAttributes = useMemo(() => {
47
+ if (isDevMode) {
48
+ return Object.assign({}, getDotContentletAttributes(contentlet, container), {
49
+ 'data-dot-object': 'contentlet'
50
+ });
51
+ }
52
+ if (isAnalyticsActive) {
53
+ return getAnalyticsContentletAttributes(contentlet);
54
+ }
55
+ return {};
56
+ }, [isDevMode, isAnalyticsActive, contentlet, container]);
43
57
  return jsx("div", Object.assign({}, dotAttributes, {
44
- "data-dot-object": "contentlet",
45
58
  className: CONTENTLET_CLASS,
46
59
  ref: ref,
47
60
  style: style,
@@ -0,0 +1,26 @@
1
+ "use client";
2
+ import { useState, useEffect } from 'react';
3
+ import { ANALYTICS_READY_EVENT, isDotAnalyticsActive } from '@dotcms/uve/internal';
4
+
5
+ /**
6
+ * @internal
7
+ * A React hook that determines whether DotCMS Analytics is active on the page.
8
+ *
9
+ * It reads the analytics active flag on mount and subscribes to the
10
+ * `dotcms:analytics:ready` event so contentlets re-render with the attributes
11
+ * Analytics needs, regardless of initialization order.
12
+ *
13
+ * @returns {boolean} - `true` when analytics is active; otherwise, `false`.
14
+ */
15
+ const useIsAnalyticsActive = () => {
16
+ const [isAnalyticsActive, setIsAnalyticsActive] = useState(false);
17
+ useEffect(() => {
18
+ const updateState = () => setIsAnalyticsActive(isDotAnalyticsActive());
19
+ updateState();
20
+ window.addEventListener(ANALYTICS_READY_EVENT, updateState);
21
+ return () => window.removeEventListener(ANALYTICS_READY_EVENT, updateState);
22
+ }, []);
23
+ return isAnalyticsActive;
24
+ };
25
+
26
+ export { useIsAnalyticsActive };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dotcms/react",
3
- "version": "1.5.5-next.2245",
3
+ "version": "1.5.5-next.2260",
4
4
  "peerDependencies": {
5
5
  "react": ">=18",
6
6
  "react-dom": ">=18"
@@ -18,7 +18,7 @@ export declare const ContainerNotFound: ({ identifier }: {
18
18
  *
19
19
  * Component to display when a container is empty.
20
20
  *
21
- * @param {DotContainerAttributes} dotAttributes
21
+ * @param {Partial<DotContainerAttributes>} dotAttributes
22
22
  * @return {*}
23
23
  */
24
- export declare const EmptyContainer: (dotAttributes: DotContainerAttributes) => import("react/jsx-runtime").JSX.Element | null;
24
+ export declare const EmptyContainer: (dotAttributes: Partial<DotContainerAttributes>) => import("react/jsx-runtime").JSX.Element | null;
@@ -0,0 +1,11 @@
1
+ /**
2
+ * @internal
3
+ * A React hook that determines whether DotCMS Analytics is active on the page.
4
+ *
5
+ * It reads the analytics active flag on mount and subscribes to the
6
+ * `dotcms:analytics:ready` event so contentlets re-render with the attributes
7
+ * Analytics needs, regardless of initialization order.
8
+ *
9
+ * @returns {boolean} - `true` when analytics is active; otherwise, `false`.
10
+ */
11
+ export declare const useIsAnalyticsActive: () => boolean;