sdk(astro,nextjs): add astro sdk and ensure window.op always first on nextjs
This commit is contained in:
3
packages/sdks/astro/README.md
Normal file
3
packages/sdks/astro/README.md
Normal file
@@ -0,0 +1,3 @@
|
||||
# OpenPanel Astro SDK
|
||||
|
||||
Read full documentation [here](https://openpanel.dev/docs/sdks/astro)
|
||||
7
packages/sdks/astro/env.d.ts
vendored
Normal file
7
packages/sdks/astro/env.d.ts
vendored
Normal file
@@ -0,0 +1,7 @@
|
||||
declare module '*.astro' {
|
||||
import type { AstroComponentFactory } from 'astro';
|
||||
const component: AstroComponentFactory;
|
||||
export default component;
|
||||
}
|
||||
|
||||
/// <reference types="astro/client" />
|
||||
46
packages/sdks/astro/index.ts
Normal file
46
packages/sdks/astro/index.ts
Normal file
@@ -0,0 +1,46 @@
|
||||
import type {
|
||||
DecrementPayload,
|
||||
IdentifyPayload,
|
||||
IncrementPayload,
|
||||
TrackProperties,
|
||||
} from '@openpanel/web';
|
||||
import IdentifyComponent from './src/IdentifyComponent.astro';
|
||||
import OpenPanelComponent from './src/OpenPanelComponent.astro';
|
||||
import SetGlobalPropertiesComponent from './src/SetGlobalPropertiesComponent.astro';
|
||||
|
||||
export * from '@openpanel/web';
|
||||
|
||||
export { OpenPanelComponent, IdentifyComponent, SetGlobalPropertiesComponent };
|
||||
|
||||
export function setGlobalProperties(properties: Record<string, unknown>) {
|
||||
window.op?.('setGlobalProperties', properties);
|
||||
}
|
||||
|
||||
export function track(name: string, properties?: TrackProperties) {
|
||||
window.op?.('track', name, properties);
|
||||
}
|
||||
|
||||
export function screenView(properties?: TrackProperties): void;
|
||||
export function screenView(path: string, properties?: TrackProperties): void;
|
||||
export function screenView(
|
||||
pathOrProperties?: string | TrackProperties,
|
||||
propertiesOrUndefined?: TrackProperties,
|
||||
) {
|
||||
window.op?.('screenView', pathOrProperties, propertiesOrUndefined);
|
||||
}
|
||||
|
||||
export function identify(payload: IdentifyPayload) {
|
||||
window.op?.('identify', payload);
|
||||
}
|
||||
|
||||
export function increment(payload: IncrementPayload) {
|
||||
window.op?.('increment', payload);
|
||||
}
|
||||
|
||||
export function decrement(payload: DecrementPayload) {
|
||||
window.op('decrement', payload);
|
||||
}
|
||||
|
||||
export function clear() {
|
||||
window.op?.('clear');
|
||||
}
|
||||
27
packages/sdks/astro/package.json
Normal file
27
packages/sdks/astro/package.json
Normal file
@@ -0,0 +1,27 @@
|
||||
{
|
||||
"name": "@openpanel/astro",
|
||||
"version": "1.0.1-local",
|
||||
"config": {
|
||||
"transformPackageJson": false,
|
||||
"transformEnvs": true
|
||||
},
|
||||
"exports": {
|
||||
".": "./index.ts"
|
||||
},
|
||||
"scripts": {
|
||||
"typecheck": "tsc --noEmit"
|
||||
},
|
||||
"files": ["src", "index.ts"],
|
||||
"keywords": ["astro-component"],
|
||||
"dependencies": {
|
||||
"@openpanel/web": "workspace:1.0.1-local"
|
||||
},
|
||||
"devDependencies": {
|
||||
"astro": "^5.7.7"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"astro": "^4.0.0 || ^5.0.0"
|
||||
},
|
||||
"private": false,
|
||||
"type": "module"
|
||||
}
|
||||
9
packages/sdks/astro/src/IdentifyComponent.astro
Normal file
9
packages/sdks/astro/src/IdentifyComponent.astro
Normal file
@@ -0,0 +1,9 @@
|
||||
---
|
||||
import type { IdentifyPayload } from '@openpanel/web';
|
||||
import { filterProps } from './asto-utils';
|
||||
interface Props extends IdentifyPayload {}
|
||||
|
||||
const props = Astro.props as Props;
|
||||
---
|
||||
|
||||
<script is:inline set:html={`window.op('identify', ${JSON.stringify(filterProps(props))});`} />
|
||||
66
packages/sdks/astro/src/OpenPanelComponent.astro
Normal file
66
packages/sdks/astro/src/OpenPanelComponent.astro
Normal file
@@ -0,0 +1,66 @@
|
||||
---
|
||||
import type {
|
||||
OpenPanelMethodNames,
|
||||
OpenPanelOptions
|
||||
} from '@openpanel/web';
|
||||
|
||||
type Props = Omit<OpenPanelOptions, 'filter'> & {
|
||||
profileId?: string;
|
||||
cdnUrl?: string;
|
||||
filter?: string;
|
||||
globalProperties?: Record<string, unknown>;
|
||||
};
|
||||
|
||||
const { profileId, cdnUrl, globalProperties, ...options } = Astro.props;
|
||||
|
||||
const CDN_URL = 'https://openpanel.dev/op1.js';
|
||||
|
||||
const stringify = (obj: unknown) => {
|
||||
if (typeof obj === 'object' && obj !== null && obj !== undefined) {
|
||||
const entries = Object.entries(obj).map(([key, value]) => {
|
||||
if (key === 'filter') {
|
||||
return `"${key}":${value}`;
|
||||
}
|
||||
return `"${key}":${JSON.stringify(value)}`;
|
||||
});
|
||||
return `{${entries.join(',')}}`;
|
||||
}
|
||||
|
||||
return JSON.stringify(obj);
|
||||
};
|
||||
|
||||
const methods: { name: OpenPanelMethodNames; value: unknown }[] = [
|
||||
{
|
||||
name: 'init',
|
||||
value: {
|
||||
...options,
|
||||
sdk: 'astro',
|
||||
sdkVersion: '1.0.1',
|
||||
},
|
||||
},
|
||||
];
|
||||
if (profileId) {
|
||||
methods.push({
|
||||
name: 'identify',
|
||||
value: {
|
||||
profileId,
|
||||
},
|
||||
});
|
||||
}
|
||||
if (globalProperties) {
|
||||
methods.push({
|
||||
name: 'setGlobalProperties',
|
||||
value: globalProperties,
|
||||
});
|
||||
}
|
||||
|
||||
const scriptContent = `window.op = window.op || function(...args) {(window.op.q = window.op.q || []).push(args)};
|
||||
${methods
|
||||
.map((method) => {
|
||||
return `window.op('${method.name}', ${stringify(method.value)});`;
|
||||
})
|
||||
.join('\n')}`;
|
||||
---
|
||||
|
||||
<script src={cdnUrl ?? CDN_URL} async defer />
|
||||
<script is:inline set:html={scriptContent} />
|
||||
@@ -0,0 +1,9 @@
|
||||
---
|
||||
import { filterProps } from './asto-utils';
|
||||
|
||||
type Props = Record<string, unknown>;
|
||||
|
||||
const props = Astro.props as Props;
|
||||
---
|
||||
|
||||
<script is:inline set:html={`window.op('setGlobalProperties', ${JSON.stringify(filterProps(props))});`} />
|
||||
7
packages/sdks/astro/src/asto-utils.ts
Normal file
7
packages/sdks/astro/src/asto-utils.ts
Normal file
@@ -0,0 +1,7 @@
|
||||
const BLACKLISTED_PROPS = ['class'];
|
||||
|
||||
export function filterProps(props: Record<string, unknown>) {
|
||||
return Object.fromEntries(
|
||||
Object.entries(props).filter(([key]) => !BLACKLISTED_PROPS.includes(key)),
|
||||
);
|
||||
}
|
||||
13
packages/sdks/astro/tsconfig.json
Normal file
13
packages/sdks/astro/tsconfig.json
Normal file
@@ -0,0 +1,13 @@
|
||||
{
|
||||
"extends": "astro/tsconfigs/strict",
|
||||
"plugins": [
|
||||
{
|
||||
"name": "@astrojs/ts-plugin"
|
||||
}
|
||||
],
|
||||
"include": [".astro/types.d.ts", "**/*"],
|
||||
"exclude": ["dist"],
|
||||
"compilerOptions": {
|
||||
"jsx": "preserve"
|
||||
}
|
||||
}
|
||||
@@ -71,6 +71,7 @@ export function OpenPanelComponent({
|
||||
<>
|
||||
<Script src={cdnUrl ?? CDN_URL} async defer />
|
||||
<Script
|
||||
strategy="beforeInteractive"
|
||||
dangerouslySetInnerHTML={{
|
||||
__html: `window.op = window.op || function(...args) {(window.op.q = window.op.q || []).push(args)};
|
||||
${methods
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@openpanel/nextjs",
|
||||
"version": "1.0.7-local",
|
||||
"version": "1.0.8-local",
|
||||
"module": "index.ts",
|
||||
"scripts": {
|
||||
"build": "rm -rf dist && tsup",
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { defineConfig } from 'tsup';
|
||||
|
||||
export default defineConfig({
|
||||
format: ['cjs', 'esm'],
|
||||
entry: ['index.tsx', 'server.ts'],
|
||||
external: ['react', 'next'],
|
||||
dts: true,
|
||||
|
||||
Reference in New Issue
Block a user