@truedat/core 8.11.0 → 8.11.1

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@truedat/core",
3
- "version": "8.11.0",
3
+ "version": "8.11.1",
4
4
  "description": "Truedat Web Core",
5
5
  "sideEffects": [
6
6
  "**/*.css",
@@ -98,5 +98,5 @@
98
98
  "swr": "^2.3.3",
99
99
  "turndown": "^7.2.2"
100
100
  },
101
- "gitHead": "89b12f5fa7ff2d0fb790d88830938ccff9cb3d91"
101
+ "gitHead": "c8c61ac1ab65f2fcda5412fe37591f784a71a5c1"
102
102
  }
@@ -8,7 +8,6 @@ import { linkTo } from "@truedat/core/routes";
8
8
  import { makeGetSubscopes } from "@truedat/core/selectors/subscopedTemplates";
9
9
  import { getConceptSubscope } from "@truedat/core/selectors/getConceptSubscope";
10
10
  import { getSidemenuGlossarySubscopes } from "@truedat/core/selectors/getSidemenuGlossarySubscopes";
11
- import TemplatesLoader from "@truedat/core/components/TemplatesLoader";
12
11
  import { useAuthorized } from "../hooks";
13
12
  import {
14
13
  CONCEPTS,
@@ -270,7 +269,6 @@ export const GlossaryMenu = ({ bgSubscopes, rootSubscopes }) => {
270
269
 
271
270
  return (
272
271
  <>
273
- <TemplatesLoader />
274
272
  <Submenu
275
273
  icon={defaultIcon}
276
274
  name="glossary"
@@ -14,6 +14,7 @@ import SidebarToggle from "./SidebarToggle";
14
14
  import TaxonomyMenu from "./TaxonomyMenu";
15
15
  import GrantMenu from "./GrantMenu";
16
16
  import MembersMenu from "./MembersMenu";
17
+ import TemplatesLoader from "./TemplatesLoader";
17
18
 
18
19
  export const SideMenu = ({
19
20
  animation = "push",
@@ -35,6 +36,7 @@ export const SideMenu = ({
35
36
  animation={animation}
36
37
  >
37
38
  <SearchMenu />
39
+ <TemplatesLoader />
38
40
  <GlossaryMenu />
39
41
  <CatalogMenu />
40
42
  <GrantMenu />
@@ -1,5 +1,6 @@
1
1
  import { render } from "@truedat/test/render";
2
2
  import GlossaryMenu from "../GlossaryMenu";
3
+ import { fetchTemplates } from "@truedat/core/routines";
3
4
 
4
5
  jest.mock("../../hooks", () => ({
5
6
  useActiveRoutes: jest.fn(() => true),
@@ -77,4 +78,20 @@ describe("<GlossaryMenu />", () => {
77
78
  expect(queryByRole("option", { name: "subscope1" })).toBeInTheDocument();
78
79
  expect(queryByRole("option", { name: "subscope2" })).toBeInTheDocument();
79
80
  });
81
+
82
+ it("does not dispatch fetchTemplates on mount (templates preload moved to SideMenu)", () => {
83
+ const dispatched = [];
84
+ render(<GlossaryMenu />, {
85
+ ...renderOpts,
86
+ dispatch: jest.fn((action) => {
87
+ dispatched.push(action);
88
+ return action;
89
+ }),
90
+ });
91
+
92
+ const fetchTemplatesCalls = dispatched.filter(
93
+ (action) => action && action.type === fetchTemplates.TRIGGER,
94
+ );
95
+ expect(fetchTemplatesCalls).toHaveLength(0);
96
+ });
80
97
  });
@@ -1,6 +1,7 @@
1
1
  import { render, waitForLoad } from "@truedat/test/render";
2
2
  import { CATALOG_VIEW_CONFIGS_QUERY } from "@truedat/core/api/queries";
3
3
  import SideMenu from "../SideMenu";
4
+ import { fetchTemplates } from "@truedat/core/routines";
4
5
 
5
6
  jest.mock("@truedat/core/hooks", () => ({
6
7
  useActiveRoutes: jest.fn(() => true),
@@ -46,4 +47,63 @@ describe("<SideMenu />", () => {
46
47
  await waitForLoad(rendered);
47
48
  expect(rendered.container).toMatchSnapshot();
48
49
  });
50
+
51
+ describe("global templates preload", () => {
52
+ let dispatched;
53
+ let useAuthorizedMock;
54
+
55
+ beforeEach(() => {
56
+ dispatched = [];
57
+ useAuthorizedMock = require("@truedat/core/hooks").useAuthorized;
58
+ useAuthorizedMock.mockReturnValue(true);
59
+ });
60
+
61
+ const renderWithDispatch = () =>
62
+ render(
63
+ <SideMenu>
64
+ <p>Hello</p>
65
+ </SideMenu>,
66
+ {
67
+ ...renderOpts,
68
+ dispatch: jest.fn((action) => {
69
+ dispatched.push(action);
70
+ return action;
71
+ }),
72
+ },
73
+ );
74
+
75
+ it("dispatches fetchTemplates with no scope on mount", async () => {
76
+ const rendered = renderWithDispatch();
77
+ await waitForLoad(rendered);
78
+ expect(dispatched).toContainEqual(
79
+ expect.objectContaining({
80
+ type: fetchTemplates.TRIGGER,
81
+ payload: { scope: undefined },
82
+ }),
83
+ );
84
+ });
85
+
86
+ it("dispatches fetchTemplates even when user lacks business_glossary_view", async () => {
87
+ useAuthorizedMock.mockImplementation((allowedRoles) => {
88
+ const roles = Array.isArray(allowedRoles)
89
+ ? allowedRoles
90
+ : [allowedRoles];
91
+ // Deny business_glossary_view/management but allow everything else.
92
+ const blocked = new Set([
93
+ "business_glossary_view",
94
+ "business_glossary_management",
95
+ ]);
96
+ return roles.some((r) => r && !blocked.has(r));
97
+ });
98
+
99
+ const rendered = renderWithDispatch();
100
+ await waitForLoad(rendered);
101
+ expect(dispatched).toContainEqual(
102
+ expect.objectContaining({
103
+ type: fetchTemplates.TRIGGER,
104
+ payload: { scope: undefined },
105
+ }),
106
+ );
107
+ });
108
+ });
49
109
  });