@pushwoosh/smart-components-kit 0.0.2 → 0.0.4
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/asyncHelpers.d.ts +1 -0
- package/asyncHelpers.js +12 -0
- package/dynamic-content-picker/DynamicContentPicker.d.ts +12 -0
- package/dynamic-content-picker/DynamicContentPicker.js +77 -0
- package/dynamic-content-picker/DynamicContentPicker.types.d.ts +9 -0
- package/dynamic-content-picker/DynamicContentPicker.types.js +1 -0
- package/dynamic-content-picker/hooks.d.ts +20 -0
- package/dynamic-content-picker/hooks.js +30 -0
- package/dynamic-content-picker/index.d.ts +3 -0
- package/dynamic-content-picker/index.js +2 -0
- package/package.json +14 -3
- package/parcel.d.ts +9 -0
- package/parcel.js +26 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function collectPaginatedData<T>(limit: number, fn: (limit: number, page: number) => Promise<T[]>): Promise<T[]>;
|
package/asyncHelpers.js
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export async function collectPaginatedData(limit, fn) {
|
|
2
|
+
const result = [];
|
|
3
|
+
let page = 0;
|
|
4
|
+
let items;
|
|
5
|
+
do {
|
|
6
|
+
// eslint-disable-next-line no-await-in-loop
|
|
7
|
+
items = await fn(limit, page);
|
|
8
|
+
result.push(...items);
|
|
9
|
+
page += 1;
|
|
10
|
+
} while (items.length === limit);
|
|
11
|
+
return result;
|
|
12
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { type FC, type PropsWithChildren, type ReactNode } from 'react';
|
|
2
|
+
import type { DynamicContent } from './DynamicContentPicker.types';
|
|
3
|
+
export declare const FieldTitle: import("styled-components").StyledComponent<"div", any, {}, never>;
|
|
4
|
+
export declare const Field: FC<PropsWithChildren<{
|
|
5
|
+
title: ReactNode;
|
|
6
|
+
}>>;
|
|
7
|
+
type DynamicContentFormProps = {
|
|
8
|
+
dc: DynamicContent;
|
|
9
|
+
onChange: (dc: DynamicContent) => void;
|
|
10
|
+
};
|
|
11
|
+
export declare const DynamicContentPicker: FC<PropsWithChildren<DynamicContentFormProps>>;
|
|
12
|
+
export {};
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import styled from 'styled-components';
|
|
3
|
+
import { Vertical } from '@pushwoosh/kit-helpers';
|
|
4
|
+
import { TextInputField } from '@pushwoosh/kit-text-input';
|
|
5
|
+
import { NativeSelect } from '@pushwoosh/kit-select';
|
|
6
|
+
import { useDynamicContentTags } from './hooks';
|
|
7
|
+
const TagPickerDiv = styled(Vertical).attrs({
|
|
8
|
+
$gap: 16,
|
|
9
|
+
$padding: 16
|
|
10
|
+
}).withConfig({
|
|
11
|
+
displayName: "TagPickerDiv",
|
|
12
|
+
componentId: "sc-j19s3d-0"
|
|
13
|
+
})(["width:240px;border-radius:4px;background:#F7F9FA;box-shadow:0 0 4px 0 rgba(0,0,0,0.06),0 4px 6px 0 rgba(0,0,0,0.06);"]);
|
|
14
|
+
export const FieldTitle = styled.div.withConfig({
|
|
15
|
+
displayName: "FieldTitle",
|
|
16
|
+
componentId: "sc-j19s3d-1"
|
|
17
|
+
})(["font-size:12px;font-style:normal;font-weight:500;line-height:130%;"]);
|
|
18
|
+
export const Field = ({
|
|
19
|
+
title,
|
|
20
|
+
children
|
|
21
|
+
}) => {
|
|
22
|
+
return React.createElement(Vertical, {
|
|
23
|
+
"$gap": 4
|
|
24
|
+
}, React.createElement(FieldTitle, null, title), children);
|
|
25
|
+
};
|
|
26
|
+
export const DynamicContentPicker = ({
|
|
27
|
+
dc,
|
|
28
|
+
onChange,
|
|
29
|
+
children
|
|
30
|
+
}) => {
|
|
31
|
+
const asyncResult = useDynamicContentTags();
|
|
32
|
+
if (asyncResult.loading) {
|
|
33
|
+
return React.createElement("div", null);
|
|
34
|
+
}
|
|
35
|
+
const tags = asyncResult.value || [];
|
|
36
|
+
const currentTag = tags.find(tag => tag.name === dc.tagName) || {
|
|
37
|
+
modifiers: ['regular']
|
|
38
|
+
};
|
|
39
|
+
return React.createElement(TagPickerDiv, null, React.createElement(Field, {
|
|
40
|
+
title: "Tag"
|
|
41
|
+
}, React.createElement(Vertical, {
|
|
42
|
+
"$gap": 8
|
|
43
|
+
}, React.createElement(NativeSelect, {
|
|
44
|
+
value: dc.tagName,
|
|
45
|
+
onChange: e => {
|
|
46
|
+
onChange({
|
|
47
|
+
tagName: e.target.value,
|
|
48
|
+
modifier: currentTag.modifiers[0],
|
|
49
|
+
defaultValue: ''
|
|
50
|
+
});
|
|
51
|
+
}
|
|
52
|
+
}, tags.map(tag => React.createElement("option", {
|
|
53
|
+
value: tag.name,
|
|
54
|
+
key: tag.name
|
|
55
|
+
}, tag.name))), React.createElement(NativeSelect, {
|
|
56
|
+
value: dc.modifier,
|
|
57
|
+
onChange: e => {
|
|
58
|
+
onChange({
|
|
59
|
+
...dc,
|
|
60
|
+
modifier: e.target.value
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
}, currentTag.modifiers.map(modifier => React.createElement("option", {
|
|
64
|
+
value: modifier,
|
|
65
|
+
key: modifier
|
|
66
|
+
}, modifier))))), React.createElement(Field, {
|
|
67
|
+
title: "Default Tag Value"
|
|
68
|
+
}, React.createElement(TextInputField, {
|
|
69
|
+
value: dc.defaultValue,
|
|
70
|
+
onChange: e => {
|
|
71
|
+
onChange({
|
|
72
|
+
...dc,
|
|
73
|
+
defaultValue: e.target.value
|
|
74
|
+
});
|
|
75
|
+
}
|
|
76
|
+
})), children);
|
|
77
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { PushwooshSPAContextType } from '../context';
|
|
2
|
+
import type { FullTagData } from './DynamicContentPicker.types';
|
|
3
|
+
export declare function fetchDynamicContentTags(context: PushwooshSPAContextType): Promise<FullTagData[]>;
|
|
4
|
+
export declare function useDynamicContentTags(): {
|
|
5
|
+
loading: boolean;
|
|
6
|
+
error?: undefined;
|
|
7
|
+
value?: undefined;
|
|
8
|
+
} | {
|
|
9
|
+
loading: false;
|
|
10
|
+
error: Error;
|
|
11
|
+
value?: undefined;
|
|
12
|
+
} | {
|
|
13
|
+
loading: true;
|
|
14
|
+
error?: Error | undefined;
|
|
15
|
+
value?: FullTagData[] | undefined;
|
|
16
|
+
} | {
|
|
17
|
+
loading: false;
|
|
18
|
+
error?: undefined;
|
|
19
|
+
value: FullTagData[];
|
|
20
|
+
};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { useContext } from 'react';
|
|
2
|
+
import { useAsync } from '@pushwoosh/kit-helpers';
|
|
3
|
+
import { collectPaginatedData } from '../asyncHelpers';
|
|
4
|
+
import { PushwooshSPAContext } from '../context';
|
|
5
|
+
const ignoreTagTypes = ['boolean', 'list'];
|
|
6
|
+
export async function fetchDynamicContentTags(context) {
|
|
7
|
+
const [originalTags, modifiers] = await Promise.all([collectPaginatedData(1000, async (perPage, page) => {
|
|
8
|
+
const res = await context.grpcBridge.tags.list({
|
|
9
|
+
orderBy: 'name',
|
|
10
|
+
orderDirection: 'asc',
|
|
11
|
+
page,
|
|
12
|
+
perPage
|
|
13
|
+
});
|
|
14
|
+
return res.tags;
|
|
15
|
+
}), context.rpcClient.callRemoteProcedure('base.modifiers', {})]);
|
|
16
|
+
const {
|
|
17
|
+
1: numbers,
|
|
18
|
+
2: strings
|
|
19
|
+
} = modifiers.response.result;
|
|
20
|
+
return originalTags.filter(tag => !ignoreTagTypes.includes(tag.type)).map(tag => ({
|
|
21
|
+
...tag,
|
|
22
|
+
modifiers: tag.type === 'integer' || tag.type === 'decimal' ? numbers : strings
|
|
23
|
+
}));
|
|
24
|
+
}
|
|
25
|
+
export function useDynamicContentTags() {
|
|
26
|
+
const context = useContext(PushwooshSPAContext);
|
|
27
|
+
return useAsync(async () => {
|
|
28
|
+
return fetchDynamicContentTags(context);
|
|
29
|
+
}, [context]);
|
|
30
|
+
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@pushwoosh/smart-components-kit",
|
|
3
3
|
"main": "index.js",
|
|
4
|
+
"module": "index.js",
|
|
4
5
|
"types": "index.d.ts",
|
|
6
|
+
"sideEffects": false,
|
|
5
7
|
"scripts": {
|
|
6
8
|
"start": "`pushwoosh-engine app:command:dev`",
|
|
7
9
|
"build": "pushwoosh-engine lib:build",
|
|
@@ -11,6 +13,13 @@
|
|
|
11
13
|
"check:types": "echo \"Run check:types\" && tsc --project tsconfig.json --skipLibCheck --emitDeclarationOnly false --noEmit"
|
|
12
14
|
},
|
|
13
15
|
"pre-commit": "check",
|
|
16
|
+
"dependencies": {
|
|
17
|
+
"@pushwoosh/kit-constants": "^1.6.5",
|
|
18
|
+
"@pushwoosh/kit-helpers": "^4.6.1",
|
|
19
|
+
"@pushwoosh/kit-select": "^1.1.0",
|
|
20
|
+
"@pushwoosh/kit-spinner": "^1.5.1",
|
|
21
|
+
"@pushwoosh/kit-text-input": "^1.5.1"
|
|
22
|
+
},
|
|
14
23
|
"devDependencies": {
|
|
15
24
|
"@eslint/js": "^9.10.0",
|
|
16
25
|
"@pushwoosh/frontend-builder-engine": "^0.6.0",
|
|
@@ -20,9 +29,12 @@
|
|
|
20
29
|
"@types/eslint__js": "^8.42.3",
|
|
21
30
|
"@types/react": "^18.3.5",
|
|
22
31
|
"@types/react-dom": "^18.3.0",
|
|
32
|
+
"@types/styled-components": "^5.1.34",
|
|
23
33
|
"eslint": "^9.10.0",
|
|
24
34
|
"react": "^18.3.1",
|
|
25
35
|
"react-dom": "^18.3.1",
|
|
36
|
+
"react-router-dom": "^5.3.4",
|
|
37
|
+
"styled-components": "^5.3.11",
|
|
26
38
|
"typescript": "^5.6.2",
|
|
27
39
|
"typescript-eslint": "^8.5.0"
|
|
28
40
|
},
|
|
@@ -31,11 +43,10 @@
|
|
|
31
43
|
"@pushwoosh/http-client": "^2.4.12",
|
|
32
44
|
"@pushwoosh/session-store": "^2.4.1",
|
|
33
45
|
"react": "^16.14.0 || ^18.0.0",
|
|
34
|
-
"react-dom": "^16.14.0 || ^18.0.0"
|
|
35
|
-
"single-spa": "^5.9.3"
|
|
46
|
+
"react-dom": "^16.14.0 || ^18.0.0"
|
|
36
47
|
},
|
|
37
48
|
"engines": {
|
|
38
49
|
"node": ">= 18"
|
|
39
50
|
},
|
|
40
|
-
"version": "0.0.
|
|
51
|
+
"version": "0.0.4"
|
|
41
52
|
}
|
package/parcel.d.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { type PushwooshSPAContextType } from './context';
|
|
2
|
+
export type ParcelResult<P> = {
|
|
3
|
+
render: (props: P) => void;
|
|
4
|
+
unmount: () => void;
|
|
5
|
+
};
|
|
6
|
+
export type ParcelProps = {
|
|
7
|
+
context: PushwooshSPAContextType;
|
|
8
|
+
};
|
|
9
|
+
export declare function parcel(container: HTMLElement): ParcelResult<ParcelProps>;
|
package/parcel.js
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { createRoot } from 'react-dom/client';
|
|
3
|
+
import { PushwooshSPAContextProvider, usePushwooshSPAContext } from './context';
|
|
4
|
+
import { DynamicContentPicker } from './dynamic-content-picker';
|
|
5
|
+
function TestParcel() {
|
|
6
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
7
|
+
const context = usePushwooshSPAContext();
|
|
8
|
+
const [dc, setDc] = React.useState({});
|
|
9
|
+
return React.createElement("div", null, React.createElement(DynamicContentPicker, {
|
|
10
|
+
dc: dc,
|
|
11
|
+
onChange: setDc
|
|
12
|
+
}));
|
|
13
|
+
}
|
|
14
|
+
export function parcel(container) {
|
|
15
|
+
const root = createRoot(container);
|
|
16
|
+
return {
|
|
17
|
+
render(props) {
|
|
18
|
+
root.render(React.createElement(PushwooshSPAContextProvider, {
|
|
19
|
+
value: props.context
|
|
20
|
+
}, React.createElement(TestParcel, null)));
|
|
21
|
+
},
|
|
22
|
+
unmount() {
|
|
23
|
+
root.unmount();
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
}
|