@voltro/plugin-posthog 0.1.0
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/CHANGELOG.md +52 -0
- package/LICENSE +57 -0
- package/README.md +26 -0
- package/SECURITY.md +56 -0
- package/THIRD-PARTY-NOTICES.md +4596 -0
- package/dist/index.d.ts +40 -0
- package/dist/index.js +104 -0
- package/package.json +44 -0
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { AnalyticsEvent } from '@voltro/runtime';
|
|
2
|
+
import { AnalyticsSinkImpl } from '@voltro/runtime';
|
|
3
|
+
import { AnalyticsSinkSpec } from '@voltro/runtime';
|
|
4
|
+
|
|
5
|
+
export { AnalyticsEvent }
|
|
6
|
+
|
|
7
|
+
export { AnalyticsSinkImpl }
|
|
8
|
+
|
|
9
|
+
export { AnalyticsSinkSpec }
|
|
10
|
+
|
|
11
|
+
export declare const posthogAnalytics: (options: PostHogAnalyticsOptions) => AnalyticsSinkSpec;
|
|
12
|
+
|
|
13
|
+
export declare interface PostHogAnalyticsOptions {
|
|
14
|
+
/** PostHog project API key (sometimes called `project_id` token). */
|
|
15
|
+
readonly apiKey: string;
|
|
16
|
+
/** API host. Default 'https://app.posthog.com'. Use 'https://eu.posthog.com'
|
|
17
|
+
* for the EU cloud or your self-hosted URL. */
|
|
18
|
+
readonly host?: string;
|
|
19
|
+
/** Opt into client-side batching (PostHog `/batch/`). Omit for immediate
|
|
20
|
+
* per-event `/capture/` delivery. See the batching note in the file
|
|
21
|
+
* header for the delivery-semantics trade-off. */
|
|
22
|
+
readonly batch?: PostHogBatchOptions;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export declare interface PostHogBatchOptions {
|
|
26
|
+
/** Flush once the buffer reaches this many events. Default 20. */
|
|
27
|
+
readonly maxSize?: number;
|
|
28
|
+
/** Flush a non-empty buffer this many ms after the first event lands
|
|
29
|
+
* (so low-volume trickles don't sit until shutdown). Default 5000. */
|
|
30
|
+
readonly flushIntervalMs?: number;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
export declare interface PostHogClient {
|
|
34
|
+
/** POST one event to `/capture/`. */
|
|
35
|
+
readonly capture: (event: AnalyticsEvent) => Promise<void>;
|
|
36
|
+
/** POST many events to `/batch/` in one request. */
|
|
37
|
+
readonly captureBatch: (events: ReadonlyArray<AnalyticsEvent>) => Promise<void>;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
export { }
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
import { Effect as e } from "effect";
|
|
2
|
+
import { createLogger as t } from "@voltro/logger";
|
|
3
|
+
import { AnalyticsCapabilityNotSupported as n, AnalyticsError as r } from "@voltro/runtime";
|
|
4
|
+
//#region src/index.ts
|
|
5
|
+
var i = "posthog", a = "https://app.posthog.com", o = 20, s = 5e3, c = t({ scope: "@voltro/plugin-posthog" }), l = (e) => ({
|
|
6
|
+
event: e.name,
|
|
7
|
+
distinct_id: e.subjectId ?? "anonymous",
|
|
8
|
+
timestamp: (e.occurredAt ?? /* @__PURE__ */ new Date()).toISOString(),
|
|
9
|
+
properties: e.tenantId !== void 0 && e.tenantId !== null ? {
|
|
10
|
+
...e.properties,
|
|
11
|
+
$tenant_id: e.tenantId
|
|
12
|
+
} : e.properties
|
|
13
|
+
}), u = (e) => {
|
|
14
|
+
let t = e.host ?? a, n = async (e, n) => {
|
|
15
|
+
let r = await fetch(`${t}${e}`, {
|
|
16
|
+
method: "POST",
|
|
17
|
+
headers: { "content-type": "application/json" },
|
|
18
|
+
body: JSON.stringify(n)
|
|
19
|
+
});
|
|
20
|
+
if (!r.ok) {
|
|
21
|
+
let t = await r.text().catch(() => "");
|
|
22
|
+
throw Error(`posthog ${e} returned HTTP ${r.status}: ${t}`);
|
|
23
|
+
}
|
|
24
|
+
};
|
|
25
|
+
return {
|
|
26
|
+
capture: (t) => n("/capture/", {
|
|
27
|
+
api_key: e.apiKey,
|
|
28
|
+
...l(t)
|
|
29
|
+
}),
|
|
30
|
+
captureBatch: (t) => n("/batch/", {
|
|
31
|
+
api_key: e.apiKey,
|
|
32
|
+
batch: t.map(l)
|
|
33
|
+
})
|
|
34
|
+
};
|
|
35
|
+
}, d = (e, t) => {
|
|
36
|
+
let n = [], r, i = () => {
|
|
37
|
+
r !== void 0 && (clearTimeout(r), r = void 0);
|
|
38
|
+
}, a = async () => {
|
|
39
|
+
if (i(), n.length === 0) return;
|
|
40
|
+
let t = n;
|
|
41
|
+
n = [];
|
|
42
|
+
try {
|
|
43
|
+
await e.captureBatch(t);
|
|
44
|
+
} catch (e) {
|
|
45
|
+
c.warn("posthog batch flush failed — dropped events", { dropped: t.length }, e);
|
|
46
|
+
}
|
|
47
|
+
};
|
|
48
|
+
return {
|
|
49
|
+
add: (e) => {
|
|
50
|
+
if (n.push(e), n.length >= t.maxSize) {
|
|
51
|
+
a();
|
|
52
|
+
return;
|
|
53
|
+
}
|
|
54
|
+
r === void 0 && (r = setTimeout(() => {
|
|
55
|
+
a();
|
|
56
|
+
}, t.flushIntervalMs), r.unref?.());
|
|
57
|
+
},
|
|
58
|
+
flush: a
|
|
59
|
+
};
|
|
60
|
+
}, f = (t) => {
|
|
61
|
+
let c = u(t), l = t.host ?? a, f = (t) => e.mapError((e) => new r({
|
|
62
|
+
provider: i,
|
|
63
|
+
operation: t,
|
|
64
|
+
cause: e instanceof Error ? `${e.name}: ${e.message}` : String(e)
|
|
65
|
+
})), p = (t) => e.fail(new n({
|
|
66
|
+
provider: i,
|
|
67
|
+
capability: t
|
|
68
|
+
})), m = t.batch ? {
|
|
69
|
+
maxSize: t.batch.maxSize ?? o,
|
|
70
|
+
flushIntervalMs: t.batch.flushIntervalMs ?? s
|
|
71
|
+
} : void 0, h = m ? d(c, m) : void 0, g = (t) => h ? e.sync(() => h.add(t)) : e.tryPromise({
|
|
72
|
+
try: () => c.capture(t),
|
|
73
|
+
catch: (e) => e
|
|
74
|
+
}).pipe(f("track")), _ = {
|
|
75
|
+
info: {
|
|
76
|
+
provider: i,
|
|
77
|
+
capabilities: {
|
|
78
|
+
track: !0,
|
|
79
|
+
aggregate: !1,
|
|
80
|
+
timeseries: !1,
|
|
81
|
+
topN: !1,
|
|
82
|
+
mirror: !1
|
|
83
|
+
},
|
|
84
|
+
detail: {
|
|
85
|
+
host: l,
|
|
86
|
+
...m ? { batch: {
|
|
87
|
+
maxSize: m.maxSize,
|
|
88
|
+
flushIntervalMs: m.flushIntervalMs
|
|
89
|
+
} } : {}
|
|
90
|
+
}
|
|
91
|
+
},
|
|
92
|
+
track: g,
|
|
93
|
+
aggregate: () => p("aggregate"),
|
|
94
|
+
timeseries: () => p("timeseries"),
|
|
95
|
+
topN: () => p("topN")
|
|
96
|
+
};
|
|
97
|
+
return {
|
|
98
|
+
kind: "posthog",
|
|
99
|
+
build: () => _,
|
|
100
|
+
...h ? { dispose: () => e.promise(() => h.flush()) } : {}
|
|
101
|
+
};
|
|
102
|
+
};
|
|
103
|
+
//#endregion
|
|
104
|
+
export { f as posthogAnalytics };
|
package/package.json
ADDED
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@voltro/plugin-posthog",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "PostHog AnalyticsSink — track-only. Forwards events to PostHog's /capture endpoint. Aggregate/timeseries/topN return AnalyticsCapabilityNotSupported because PostHog's analytics live in their UI/SQL, not in a generic API. Compose with another sink for the reads.",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"voltro",
|
|
7
|
+
"typescript",
|
|
8
|
+
"framework"
|
|
9
|
+
],
|
|
10
|
+
"license": "SEE LICENSE IN LICENSE",
|
|
11
|
+
"homepage": "https://voltro.dev",
|
|
12
|
+
"bugs": {
|
|
13
|
+
"email": "support@voltro.dev"
|
|
14
|
+
},
|
|
15
|
+
"author": {
|
|
16
|
+
"name": "Voltro UG",
|
|
17
|
+
"url": "https://voltro.dev"
|
|
18
|
+
},
|
|
19
|
+
"type": "module",
|
|
20
|
+
"exports": {
|
|
21
|
+
".": {
|
|
22
|
+
"types": "./dist/index.d.ts",
|
|
23
|
+
"import": "./dist/index.js",
|
|
24
|
+
"default": "./dist/index.js"
|
|
25
|
+
}
|
|
26
|
+
},
|
|
27
|
+
"main": "./dist/index.js",
|
|
28
|
+
"module": "./dist/index.js",
|
|
29
|
+
"types": "./dist/index.d.ts",
|
|
30
|
+
"sideEffects": false,
|
|
31
|
+
"engines": {
|
|
32
|
+
"node": ">=24.0.0"
|
|
33
|
+
},
|
|
34
|
+
"dependencies": {
|
|
35
|
+
"@voltro/logger": "0.1.0",
|
|
36
|
+
"@voltro/runtime": "0.1.0"
|
|
37
|
+
},
|
|
38
|
+
"peerDependencies": {
|
|
39
|
+
"effect": "^3.21.4"
|
|
40
|
+
},
|
|
41
|
+
"publishConfig": {
|
|
42
|
+
"access": "public"
|
|
43
|
+
}
|
|
44
|
+
}
|