cakranala 0.0.0-stage → 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/LICENSE +202 -0
- package/README.md +113 -2
- package/bin/cakranala.js +15 -0
- package/dist/cli/index.js +23 -0
- package/dist/collect/browser.d.ts +24 -0
- package/dist/collect/facebook.d.ts +19 -0
- package/dist/collect/index.d.ts +66 -0
- package/dist/collect/index.js +4 -0
- package/dist/collect/instagram.d.ts +20 -0
- package/dist/collect/telegram.d.ts +2 -0
- package/dist/collect/tiktok.d.ts +28 -0
- package/dist/collect/x.d.ts +37 -0
- package/dist/collect/youtube.d.ts +14 -0
- package/dist/embed/embed.d.ts +13 -0
- package/dist/embed/index.d.ts +2 -0
- package/dist/embed/index.js +2 -0
- package/dist/embed/reason.d.ts +10 -0
- package/dist/engine/detect/consensus.d.ts +40 -0
- package/dist/engine/detect/forensics.d.ts +20 -0
- package/dist/engine/detect/graph.d.ts +44 -0
- package/dist/engine/detect/index.d.ts +52 -0
- package/dist/engine/detect/layers.d.ts +32 -0
- package/dist/engine/evaluate.d.ts +23 -0
- package/dist/engine/index.d.ts +13 -0
- package/dist/engine/ports.d.ts +10 -0
- package/dist/engine/privacy.d.ts +2 -0
- package/dist/engine/schema.d.ts +40 -0
- package/dist/engine/shield.d.ts +57 -0
- package/dist/engine/simulate.d.ts +45 -0
- package/dist/engine/text.d.ts +9 -0
- package/dist/engine/util.d.ts +26 -0
- package/dist/home.d.ts +2 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +17 -0
- package/dist/web/apple-touch-icon-5nx1caa0.png +0 -0
- package/dist/web/chunk-0p6gbr4g.css +1 -0
- package/dist/web/chunk-8rhsy347.js +430 -0
- package/dist/web/favicon-vjre31pg.ico +0 -0
- package/dist/web/favicon-ze8spk31.svg +1 -0
- package/dist/web/index.html +19 -0
- package/dist/web/index.js +186 -0
- package/package.json +92 -4
- package/scenarios/seruni.json +486 -0
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
import { type Dataset } from "../engine";
|
|
2
|
+
export interface SidecarConfig {
|
|
3
|
+
baseUrl: string;
|
|
4
|
+
username: string;
|
|
5
|
+
password: string;
|
|
6
|
+
}
|
|
7
|
+
export declare function sidecarFromEnv(env?: Record<string, string | undefined>): SidecarConfig | undefined;
|
|
8
|
+
export declare function tiktokAccount(cookie: string, userAgent?: string): Promise<{
|
|
9
|
+
id: string;
|
|
10
|
+
handle: string;
|
|
11
|
+
name: string;
|
|
12
|
+
}>;
|
|
13
|
+
export declare function createTiktokCollector(config: SidecarConfig): {
|
|
14
|
+
check(cookies: string, userAgent?: string): Promise<{
|
|
15
|
+
authenticated: boolean;
|
|
16
|
+
browser: string;
|
|
17
|
+
}>;
|
|
18
|
+
importIdentity(cookies: string, userAgent?: string): Promise<string>;
|
|
19
|
+
search(keyword: string, o?: {
|
|
20
|
+
videos?: number;
|
|
21
|
+
pages?: number;
|
|
22
|
+
identity?: string;
|
|
23
|
+
}): Promise<Dataset>;
|
|
24
|
+
video(contentId: string, o?: {
|
|
25
|
+
pages?: number;
|
|
26
|
+
identity?: string;
|
|
27
|
+
}): Promise<Dataset>;
|
|
28
|
+
};
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import { type Actor, type Dataset } from "../engine";
|
|
2
|
+
export interface XSession {
|
|
3
|
+
authToken: string;
|
|
4
|
+
ct0: string;
|
|
5
|
+
userAgent: string;
|
|
6
|
+
proxy?: string;
|
|
7
|
+
}
|
|
8
|
+
export interface Profile {
|
|
9
|
+
id: string;
|
|
10
|
+
handle: string;
|
|
11
|
+
name: string;
|
|
12
|
+
followers?: number;
|
|
13
|
+
createdAt?: number;
|
|
14
|
+
}
|
|
15
|
+
export interface SearchOptions {
|
|
16
|
+
pages?: number;
|
|
17
|
+
since?: string;
|
|
18
|
+
lang?: string;
|
|
19
|
+
delayMs?: [number, number];
|
|
20
|
+
onPage?: (info: {
|
|
21
|
+
page: number;
|
|
22
|
+
tweets: number;
|
|
23
|
+
remaining: number | null;
|
|
24
|
+
}) => void;
|
|
25
|
+
}
|
|
26
|
+
export interface XRateState {
|
|
27
|
+
remaining: number | null;
|
|
28
|
+
reset: number | null;
|
|
29
|
+
}
|
|
30
|
+
export declare function createXCollector(session: XSession): Promise<{
|
|
31
|
+
rate: XRateState;
|
|
32
|
+
search(query: string, o?: SearchOptions): Promise<Dataset>;
|
|
33
|
+
me(): Promise<Profile>;
|
|
34
|
+
retweeters(id: string, pages?: number): Promise<Actor[]>;
|
|
35
|
+
conversation(id: string, o?: Pick<SearchOptions, "pages" | "delayMs">): Promise<Dataset>;
|
|
36
|
+
}>;
|
|
37
|
+
export declare function sessionFromEnv(env?: Record<string, string | undefined>): XSession | undefined;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { type Dataset } from "../engine";
|
|
2
|
+
export interface YoutubeOptions {
|
|
3
|
+
videos?: number;
|
|
4
|
+
pages?: number;
|
|
5
|
+
}
|
|
6
|
+
export declare function createYoutubeCollector(cookie?: string, proxy?: string): Promise<{
|
|
7
|
+
me(): Promise<{
|
|
8
|
+
id: string;
|
|
9
|
+
handle: any;
|
|
10
|
+
name: any;
|
|
11
|
+
}>;
|
|
12
|
+
search(query: string, o?: YoutubeOptions): Promise<Dataset>;
|
|
13
|
+
video(id: string, o?: YoutubeOptions): Promise<Dataset>;
|
|
14
|
+
}>;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { Embedder } from "../engine";
|
|
2
|
+
export declare const MODEL = "Xenova/multilingual-e5-small";
|
|
3
|
+
export interface E5Options {
|
|
4
|
+
model?: string;
|
|
5
|
+
dtype?: "fp32" | "fp16" | "q8" | "q4";
|
|
6
|
+
batch?: number;
|
|
7
|
+
progress?: (file: string, loaded: number, total: number) => void;
|
|
8
|
+
}
|
|
9
|
+
type Transformers = typeof import("@huggingface/transformers");
|
|
10
|
+
export declare function transformers(): Promise<Transformers | undefined>;
|
|
11
|
+
export declare const modelCached: (model?: string) => boolean;
|
|
12
|
+
export declare function createE5Embedder(opts?: E5Options): Promise<Embedder>;
|
|
13
|
+
export {};
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
import{existsSync as h}from"fs";import{createRequire as _}from"module";import{join as s}from"path";import{pathToFileURL as O}from"url";import{homedir as L}from"os";import{join as g,resolve as y}from"path";var D=()=>y(process.env.CAKRANALA_DATA??".cakranala"),m=()=>y(process.env.CAKRANALA_CACHE??g(process.env.XDG_CACHE_HOME??g(L(),".cache"),"cakranala"));var l="Xenova/multilingual-e5-small";async function E(){let e=await import("@huggingface/transformers").catch(()=>{return});if(e)return e;let r=s(m(),"deps");if(!h(s(r,"node_modules","@huggingface","transformers")))return;return import(O(_(s(r,"package.json")).resolve("@huggingface/transformers")).href)}var R=(e=l)=>h(s(m(),"models",e));async function M(e={}){let r=await E();if(!r)throw Error("layer semantik butuh @huggingface/transformers, jalankan: cakranala install");r.env.cacheDir=s(m(),"models");let o=r.pipeline,c=e.progress&&((t)=>t.status==="progress"&&e.progress(t.file??"",t.loaded??0,t.total??0)),n=await o("feature-extraction",e.model??l,{dtype:e.dtype??"q8",progress_callback:c}),p=e.batch??64;return{async embed(t){let d=[];for(let i=0;i<t.length;i+=p){let u=await n(t.slice(i,i+p).map((a)=>`query: ${a}`),{pooling:"mean",normalize:!0}),[A,f]=u.dims,x=u.data;for(let a=0;a<A;a++)d.push(x.slice(a*f,(a+1)*f))}return d}}}function b(e){return{async complete(r,o={}){let c=o.images?.length?[{type:"text",text:r},...o.images.map((t)=>({type:"image_url",image_url:{url:t}}))]:r,n=await fetch(`${e.baseUrl.replace(/\/$/,"")}/chat/completions`,{method:"POST",headers:{...e.apiKey?{Authorization:`Bearer ${e.apiKey}`}:{},"Content-Type":"application/json"},signal:AbortSignal.timeout(e.timeoutMs??120000),body:JSON.stringify({model:e.model,temperature:e.temperature??0.7,messages:[...o.system?[{role:"system",content:o.system}]:[],{role:"user",content:c}],...o.json?{response_format:{type:"json_object"}}:{}})});if(!n.ok)throw Error(`reasoner ${n.status}: ${(await n.text()).slice(0,200)}`);return(await n.json()).choices[0].message.content}}}function w(e=process.env){if(!e.LLM_BASE_URL||!e.LLM_MODEL)return;return b({baseUrl:e.LLM_BASE_URL,apiKey:e.LLM_API_KEY,model:e.LLM_MODEL})}export{l as MODEL,M as createE5Embedder,b as createReasoner,R as modelCached,w as reasonerFromEnv,E as transformers};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { Reasoner } from "../engine";
|
|
2
|
+
export interface OpenAIReasonerOptions {
|
|
3
|
+
baseUrl: string;
|
|
4
|
+
apiKey?: string;
|
|
5
|
+
model: string;
|
|
6
|
+
temperature?: number;
|
|
7
|
+
timeoutMs?: number;
|
|
8
|
+
}
|
|
9
|
+
export declare function createReasoner(o: OpenAIReasonerOptions): Reasoner;
|
|
10
|
+
export declare function reasonerFromEnv(env?: Record<string, string | undefined>): Reasoner | undefined;
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { Event } from "../schema";
|
|
2
|
+
import type { Cluster } from "./graph";
|
|
3
|
+
export interface Sie {
|
|
4
|
+
value: number;
|
|
5
|
+
ci: [number, number];
|
|
6
|
+
}
|
|
7
|
+
export interface Narrative {
|
|
8
|
+
id: string;
|
|
9
|
+
sample: string;
|
|
10
|
+
tags: string[];
|
|
11
|
+
supporters: number;
|
|
12
|
+
events: number;
|
|
13
|
+
sie: Sie;
|
|
14
|
+
iks: number;
|
|
15
|
+
coordinated: number;
|
|
16
|
+
verdict: "manufactured" | "organic";
|
|
17
|
+
p: number;
|
|
18
|
+
clusters: {
|
|
19
|
+
id: string;
|
|
20
|
+
actors: number;
|
|
21
|
+
p: number;
|
|
22
|
+
}[];
|
|
23
|
+
counterfactual: {
|
|
24
|
+
binSec: number;
|
|
25
|
+
start: number;
|
|
26
|
+
all: number[];
|
|
27
|
+
organic: number[];
|
|
28
|
+
};
|
|
29
|
+
}
|
|
30
|
+
export declare function sie(supporters: string[], membership: Map<string, Cluster>): number;
|
|
31
|
+
export interface HeldOut {
|
|
32
|
+
clusterOf: (e: Event) => Cluster | undefined;
|
|
33
|
+
baseRate: number;
|
|
34
|
+
}
|
|
35
|
+
export declare function narratives(events: Event[], clusters: Cluster[], frames: Map<number, number> | undefined, opts: {
|
|
36
|
+
minSupporters: number;
|
|
37
|
+
seed: number;
|
|
38
|
+
alpha: number;
|
|
39
|
+
syncSec: number;
|
|
40
|
+
}, heldOut?: HeldOut): Narrative[];
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { Event } from "../schema";
|
|
2
|
+
export interface Forensics {
|
|
3
|
+
onset: {
|
|
4
|
+
ts: number;
|
|
5
|
+
actors: number;
|
|
6
|
+
windowSec: number;
|
|
7
|
+
};
|
|
8
|
+
waves: number;
|
|
9
|
+
seeders: {
|
|
10
|
+
actor: string;
|
|
11
|
+
leadScore: number;
|
|
12
|
+
}[];
|
|
13
|
+
rotation: number | null;
|
|
14
|
+
cadence: {
|
|
15
|
+
medianSec: number;
|
|
16
|
+
cv: number;
|
|
17
|
+
} | null;
|
|
18
|
+
talkingPoints: string[];
|
|
19
|
+
}
|
|
20
|
+
export declare function forensics(members: string[], all: Event[], gapSec?: number): Forensics;
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import type { LayerId, LayerResult, PairStat } from "./layers";
|
|
2
|
+
export interface Edge {
|
|
3
|
+
a: string;
|
|
4
|
+
b: string;
|
|
5
|
+
rho: number;
|
|
6
|
+
p: number;
|
|
7
|
+
layers: Partial<Record<LayerId, PairStat>>;
|
|
8
|
+
}
|
|
9
|
+
export interface LayerEvidence {
|
|
10
|
+
layer: LayerId;
|
|
11
|
+
pairs: number;
|
|
12
|
+
meanEpisodes: number;
|
|
13
|
+
meanObserved: number;
|
|
14
|
+
meanExpected: number;
|
|
15
|
+
}
|
|
16
|
+
export interface Cluster {
|
|
17
|
+
id: string;
|
|
18
|
+
members: string[];
|
|
19
|
+
rho: number;
|
|
20
|
+
p: number;
|
|
21
|
+
score: number;
|
|
22
|
+
families: {
|
|
23
|
+
layers: LayerId[];
|
|
24
|
+
strength: number;
|
|
25
|
+
}[];
|
|
26
|
+
layers: LayerEvidence[];
|
|
27
|
+
}
|
|
28
|
+
export interface Fusion {
|
|
29
|
+
families: LayerId[][];
|
|
30
|
+
minFamilies: number;
|
|
31
|
+
edgeAlphas: number[];
|
|
32
|
+
fdr: number;
|
|
33
|
+
}
|
|
34
|
+
export declare function detect(results: LayerResult[], o: Fusion & {
|
|
35
|
+
minClusterSize: number;
|
|
36
|
+
minDegree: number;
|
|
37
|
+
seed: number;
|
|
38
|
+
}): {
|
|
39
|
+
real: Map<string, number>;
|
|
40
|
+
edges: Edge[];
|
|
41
|
+
clusters: Cluster[];
|
|
42
|
+
alpha: number;
|
|
43
|
+
decoyFdr: number;
|
|
44
|
+
};
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import type { Dataset } from "../schema";
|
|
2
|
+
import type { Embedder, Reasoner } from "../ports";
|
|
3
|
+
import { type LayerId, type LayerOptions } from "./layers";
|
|
4
|
+
import { type Cluster, type Edge } from "./graph";
|
|
5
|
+
import { type Forensics } from "./forensics";
|
|
6
|
+
import { type Narrative } from "./consensus";
|
|
7
|
+
export interface AnalyzeOptions extends LayerOptions {
|
|
8
|
+
layers: LayerId[];
|
|
9
|
+
families: LayerId[][];
|
|
10
|
+
minFamilies: number;
|
|
11
|
+
edgeAlphas: number[];
|
|
12
|
+
fdr: number;
|
|
13
|
+
clusterAlpha: number;
|
|
14
|
+
minClusterSize: number;
|
|
15
|
+
minDegree: number;
|
|
16
|
+
minClusterRho: number;
|
|
17
|
+
minSupporters: number;
|
|
18
|
+
verdictAlpha: number;
|
|
19
|
+
syncSec: number;
|
|
20
|
+
verdictFolds: 1 | 2;
|
|
21
|
+
embedder?: Embedder;
|
|
22
|
+
reasoner?: Reasoner;
|
|
23
|
+
}
|
|
24
|
+
export interface ClusterReport extends Cluster {
|
|
25
|
+
forensics: Forensics;
|
|
26
|
+
brief?: string;
|
|
27
|
+
}
|
|
28
|
+
export interface Report {
|
|
29
|
+
generatedAt: number;
|
|
30
|
+
stats: {
|
|
31
|
+
actors: number;
|
|
32
|
+
events: number;
|
|
33
|
+
flaggedActors: number;
|
|
34
|
+
layersRun: LayerId[];
|
|
35
|
+
};
|
|
36
|
+
tests: Partial<Record<LayerId, {
|
|
37
|
+
candidates: number;
|
|
38
|
+
nominal: number;
|
|
39
|
+
dispersion: number;
|
|
40
|
+
}>>;
|
|
41
|
+
null: {
|
|
42
|
+
replicates: number;
|
|
43
|
+
alpha: number;
|
|
44
|
+
decoyFdr: number;
|
|
45
|
+
};
|
|
46
|
+
edges: Edge[];
|
|
47
|
+
clusters: ClusterReport[];
|
|
48
|
+
narratives: Narrative[];
|
|
49
|
+
scores: Record<string, number>;
|
|
50
|
+
}
|
|
51
|
+
export declare const DEFAULTS: AnalyzeOptions;
|
|
52
|
+
export declare function analyze(ds: Dataset, options?: Partial<AnalyzeOptions>): Promise<Report>;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import type { Dataset } from "../schema";
|
|
2
|
+
export type LayerId = "coaction" | "coframing" | "rhythm" | "copypasta" | "lifecycle";
|
|
3
|
+
export declare const LAYERS: LayerId[];
|
|
4
|
+
export interface LayerOptions {
|
|
5
|
+
windowSec: Partial<Record<LayerId, number>>;
|
|
6
|
+
similarityQuantile: number;
|
|
7
|
+
copypastaFloor: number;
|
|
8
|
+
minEpisodes: number;
|
|
9
|
+
maxGroup: number;
|
|
10
|
+
groupQuantile: number;
|
|
11
|
+
nullReplicates: number;
|
|
12
|
+
shiftMax: number;
|
|
13
|
+
strataWindows: number;
|
|
14
|
+
seed: number;
|
|
15
|
+
}
|
|
16
|
+
export declare const LAYER_DEFAULTS: LayerOptions;
|
|
17
|
+
export interface PairStat {
|
|
18
|
+
w: number;
|
|
19
|
+
observed: number;
|
|
20
|
+
expected: number;
|
|
21
|
+
p: number;
|
|
22
|
+
episodes: number;
|
|
23
|
+
}
|
|
24
|
+
export interface LayerResult {
|
|
25
|
+
id: LayerId;
|
|
26
|
+
candidates: number;
|
|
27
|
+
dispersion: number;
|
|
28
|
+
pairs: Map<string, PairStat>;
|
|
29
|
+
replicates: Map<string, number>[];
|
|
30
|
+
}
|
|
31
|
+
export declare const handleShape: (handle?: string) => string;
|
|
32
|
+
export declare function runLayers(ds: Dataset, opts: LayerOptions, enabled: LayerId[], frames?: Map<number, number>): LayerResult[];
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import type { Truth } from "./schema";
|
|
2
|
+
import type { Report } from "./detect";
|
|
3
|
+
export interface Evaluation {
|
|
4
|
+
precision: number;
|
|
5
|
+
recall: number;
|
|
6
|
+
f1: number;
|
|
7
|
+
operations: {
|
|
8
|
+
id: string;
|
|
9
|
+
kind: string;
|
|
10
|
+
size: number;
|
|
11
|
+
recall: number;
|
|
12
|
+
}[];
|
|
13
|
+
organicFlagRate: number;
|
|
14
|
+
viralFlagRate: number | null;
|
|
15
|
+
}
|
|
16
|
+
export declare function evaluate(report: Report, truth: Truth): Evaluation;
|
|
17
|
+
export interface Ranking {
|
|
18
|
+
ap: number;
|
|
19
|
+
prevalence: number;
|
|
20
|
+
lift: number;
|
|
21
|
+
precisionAt: Record<string, number>;
|
|
22
|
+
}
|
|
23
|
+
export declare function ranking(scores: Record<string, number>, truth: Truth, ks?: number[]): Ranking;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
export * from "./schema";
|
|
2
|
+
export type { Embedder, Reasoner } from "./ports";
|
|
3
|
+
export { analyze, DEFAULTS, type AnalyzeOptions, type Report, type ClusterReport } from "./detect";
|
|
4
|
+
export { LAYERS, type LayerId } from "./detect/layers";
|
|
5
|
+
export type { Edge, Cluster } from "./detect/graph";
|
|
6
|
+
export type { Narrative, Sie } from "./detect/consensus";
|
|
7
|
+
export type { Forensics } from "./detect/forensics";
|
|
8
|
+
export { simulate, generateScenario, enrichScenario, type Scenario, type OperationKind } from "./simulate";
|
|
9
|
+
export { evaluate, ranking, type Evaluation, type Ranking } from "./evaluate";
|
|
10
|
+
export { shield, type ShieldInput, type ShieldContext, type ShieldResult, type UrlFinding, type Match } from "./shield";
|
|
11
|
+
export { pseudonymize } from "./privacy";
|
|
12
|
+
export { normalize, plain } from "./text";
|
|
13
|
+
export { uuidFrom } from "./util";
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export declare const SCHEMA_VERSION = 1;
|
|
2
|
+
export type Action = "post" | "reply" | "quote" | "reshare" | "comment" | "react";
|
|
3
|
+
export type TimePrecision = "ms" | "s" | "min" | "approx";
|
|
4
|
+
export interface Actor {
|
|
5
|
+
id: string;
|
|
6
|
+
platform: string;
|
|
7
|
+
handle?: string;
|
|
8
|
+
createdAt?: number;
|
|
9
|
+
followers?: number;
|
|
10
|
+
following?: number;
|
|
11
|
+
posts?: number;
|
|
12
|
+
reshared?: string[];
|
|
13
|
+
shape?: string;
|
|
14
|
+
}
|
|
15
|
+
export interface Event {
|
|
16
|
+
id: string;
|
|
17
|
+
actor: string;
|
|
18
|
+
action: Action;
|
|
19
|
+
ts: number;
|
|
20
|
+
precision?: TimePrecision;
|
|
21
|
+
target?: string;
|
|
22
|
+
text?: string;
|
|
23
|
+
tags?: string[];
|
|
24
|
+
urls?: string[];
|
|
25
|
+
lang?: string;
|
|
26
|
+
}
|
|
27
|
+
export type Truth = Record<string, string>;
|
|
28
|
+
export interface Dataset {
|
|
29
|
+
version: typeof SCHEMA_VERSION;
|
|
30
|
+
actors: Actor[];
|
|
31
|
+
events: Event[];
|
|
32
|
+
truth?: Truth;
|
|
33
|
+
meta?: {
|
|
34
|
+
source?: string;
|
|
35
|
+
query?: string;
|
|
36
|
+
coverage?: number;
|
|
37
|
+
collectedAt?: number;
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
export declare function validate(input: unknown): Dataset;
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import type { Embedder, Reasoner } from "./ports";
|
|
2
|
+
import type { Report } from "./detect";
|
|
3
|
+
export interface ShieldInput {
|
|
4
|
+
text?: string;
|
|
5
|
+
image?: string;
|
|
6
|
+
}
|
|
7
|
+
export interface ShieldContext {
|
|
8
|
+
report?: Report;
|
|
9
|
+
officialDomains?: string[];
|
|
10
|
+
library?: {
|
|
11
|
+
claim: string;
|
|
12
|
+
verdict: string;
|
|
13
|
+
source?: string;
|
|
14
|
+
title?: string;
|
|
15
|
+
}[];
|
|
16
|
+
taxonomy?: {
|
|
17
|
+
id: string;
|
|
18
|
+
name: string;
|
|
19
|
+
description: string;
|
|
20
|
+
}[];
|
|
21
|
+
embedder?: Embedder;
|
|
22
|
+
reasoner?: Reasoner;
|
|
23
|
+
}
|
|
24
|
+
export interface UrlFinding {
|
|
25
|
+
url: string;
|
|
26
|
+
host: string;
|
|
27
|
+
flags: string[];
|
|
28
|
+
imitates?: string;
|
|
29
|
+
}
|
|
30
|
+
export interface Match {
|
|
31
|
+
kind: "narasi" | "klaster" | "pustaka";
|
|
32
|
+
ref: string;
|
|
33
|
+
similarity: number;
|
|
34
|
+
text: string;
|
|
35
|
+
supporters?: number;
|
|
36
|
+
sie?: number;
|
|
37
|
+
iks?: number;
|
|
38
|
+
verdict?: string;
|
|
39
|
+
title?: string;
|
|
40
|
+
}
|
|
41
|
+
export interface ShieldResult {
|
|
42
|
+
text: string;
|
|
43
|
+
risk: "rendah" | "sedang" | "tinggi";
|
|
44
|
+
score: number;
|
|
45
|
+
cues: string[];
|
|
46
|
+
urls: UrlFinding[];
|
|
47
|
+
techniques: {
|
|
48
|
+
id?: string;
|
|
49
|
+
name: string;
|
|
50
|
+
quote: string;
|
|
51
|
+
why: string;
|
|
52
|
+
}[];
|
|
53
|
+
matches: Match[];
|
|
54
|
+
summary?: string;
|
|
55
|
+
advice: string[];
|
|
56
|
+
}
|
|
57
|
+
export declare function shield(input: ShieldInput, ctx?: ShieldContext): Promise<ShieldResult>;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { type Dataset } from "./schema";
|
|
2
|
+
import type { Reasoner } from "./ports";
|
|
3
|
+
export type OperationKind = "paid" | "botfarm" | "swarm";
|
|
4
|
+
export interface Scenario {
|
|
5
|
+
name: string;
|
|
6
|
+
durationMin: number;
|
|
7
|
+
organic: {
|
|
8
|
+
actors: number;
|
|
9
|
+
hubs: number;
|
|
10
|
+
eventsPerActor: number;
|
|
11
|
+
narrativeShare: number;
|
|
12
|
+
};
|
|
13
|
+
topics: {
|
|
14
|
+
texts: string[];
|
|
15
|
+
tags?: string[];
|
|
16
|
+
}[];
|
|
17
|
+
narratives: {
|
|
18
|
+
id: string;
|
|
19
|
+
claims: string[];
|
|
20
|
+
organicTakes: string[];
|
|
21
|
+
tags: string[];
|
|
22
|
+
paraphrases?: string[];
|
|
23
|
+
}[];
|
|
24
|
+
viral?: {
|
|
25
|
+
atMin: number;
|
|
26
|
+
size: number;
|
|
27
|
+
texts: string[];
|
|
28
|
+
tags: string[];
|
|
29
|
+
};
|
|
30
|
+
operations: {
|
|
31
|
+
id: string;
|
|
32
|
+
kind: OperationKind;
|
|
33
|
+
size: number;
|
|
34
|
+
narrative: string;
|
|
35
|
+
waves: number;
|
|
36
|
+
}[];
|
|
37
|
+
fillers: {
|
|
38
|
+
openers: string[];
|
|
39
|
+
closers: string[];
|
|
40
|
+
emoji: string[];
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
export declare function simulate(scenario: Scenario, seed?: number): Dataset;
|
|
44
|
+
export declare function generateScenario(reasoner: Reasoner, theme: string, base: Scenario): Promise<Scenario>;
|
|
45
|
+
export declare function enrichScenario(reasoner: Reasoner, scenario: Scenario, count?: number): Promise<Scenario>;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export declare function normalize(text: string): string;
|
|
2
|
+
export declare const tokens: (text: string) => string[];
|
|
3
|
+
export declare function shingles(text: string, n?: number): Set<string>;
|
|
4
|
+
export declare function jaccard(a: Set<string>, b: Set<string>): number;
|
|
5
|
+
export declare function nearDuplicateGroups(texts: string[], threshold: number): number[];
|
|
6
|
+
export declare function centered(vectors: Float32Array[]): Float32Array<ArrayBuffer>[];
|
|
7
|
+
export declare function cosine(a: Float32Array, b: Float32Array): number;
|
|
8
|
+
export declare function kmeans(vectors: Float32Array[], k: number, r: () => number, iterations?: number): number[];
|
|
9
|
+
export declare const plain: (s: string) => string;
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
export type Rng = () => number;
|
|
2
|
+
export declare function rng(seed: number): Rng;
|
|
3
|
+
export declare const pick: <T>(r: Rng, xs: readonly T[]) => T;
|
|
4
|
+
export declare function gauss(r: Rng, mean?: number, sd?: number): number;
|
|
5
|
+
export declare const expo: (r: Rng, mean: number) => number;
|
|
6
|
+
export declare function hash32(s: string, seed?: number): number;
|
|
7
|
+
export declare const pairKey: (a: string, b: string) => string;
|
|
8
|
+
export declare const splitPair: (k: string) => [string, string];
|
|
9
|
+
export declare function quantile(xs: number[], q: number): number;
|
|
10
|
+
export declare const mean: (xs: number[]) => number;
|
|
11
|
+
export declare function groupBy<T, K>(xs: Iterable<T>, key: (x: T) => K): Map<K, T[]>;
|
|
12
|
+
export declare class UnionFind {
|
|
13
|
+
private p;
|
|
14
|
+
constructor(n: number);
|
|
15
|
+
find(i: number): number;
|
|
16
|
+
union(a: number, b: number): void;
|
|
17
|
+
}
|
|
18
|
+
export declare function randomPairQuantile(n: number, sim: (i: number, j: number) => number, q: number, r: Rng, samples?: number): number;
|
|
19
|
+
export declare function poissonTail(k: number, lambda: number): number;
|
|
20
|
+
export declare function shuffle<T>(r: Rng, xs: T[]): T[];
|
|
21
|
+
export declare function binomialTail(k: number, n: number, p: number): number;
|
|
22
|
+
export declare function uuidFrom(input: string): string;
|
|
23
|
+
export declare function lgamma(x: number): number;
|
|
24
|
+
export declare function nbTail(k: number, mu: number, dispersion: number): number;
|
|
25
|
+
export declare function cauchyCombine(ps: number[]): number;
|
|
26
|
+
export declare function partialConjunction(ps: number[], u: number): number;
|
package/dist/home.d.ts
ADDED
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./engine";
|