@helyx/module-automod 1.0.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.
Files changed (79) hide show
  1. package/CHANGELOG.md +30 -0
  2. package/LICENSE +725 -0
  3. package/README.md +80 -0
  4. package/dist/activity-resource.d.ts +3 -0
  5. package/dist/activity-resource.js +114 -0
  6. package/dist/case-link-provider.d.ts +3 -0
  7. package/dist/case-link-provider.js +13 -0
  8. package/dist/configuration.d.ts +22 -0
  9. package/dist/configuration.js +85 -0
  10. package/dist/constants.d.ts +30 -0
  11. package/dist/constants.js +37 -0
  12. package/dist/contracts.d.ts +30 -0
  13. package/dist/contracts.js +51 -0
  14. package/dist/domain.d.ts +61 -0
  15. package/dist/domain.js +274 -0
  16. package/dist/engine/canonicalisation.d.ts +9 -0
  17. package/dist/engine/canonicalisation.js +150 -0
  18. package/dist/engine/compile.d.ts +4 -0
  19. package/dist/engine/compile.js +169 -0
  20. package/dist/engine/confidence.d.ts +13 -0
  21. package/dist/engine/confidence.js +57 -0
  22. package/dist/engine/configuration-cache.d.ts +29 -0
  23. package/dist/engine/configuration-cache.js +115 -0
  24. package/dist/engine/contracts.d.ts +82 -0
  25. package/dist/engine/contracts.js +25 -0
  26. package/dist/engine/index.d.ts +11 -0
  27. package/dist/engine/index.js +11 -0
  28. package/dist/engine/matcher.d.ts +3 -0
  29. package/dist/engine/matcher.js +206 -0
  30. package/dist/engine/observations.d.ts +45 -0
  31. package/dist/engine/observations.js +105 -0
  32. package/dist/engine/operation-id.d.ts +18 -0
  33. package/dist/engine/operation-id.js +24 -0
  34. package/dist/engine/similar-message-window.d.ts +68 -0
  35. package/dist/engine/similar-message-window.js +259 -0
  36. package/dist/engine/term-import.d.ts +15 -0
  37. package/dist/engine/term-import.js +43 -0
  38. package/dist/enhanced-configuration.d.ts +16 -0
  39. package/dist/enhanced-configuration.js +91 -0
  40. package/dist/events.d.ts +4 -0
  41. package/dist/events.js +371 -0
  42. package/dist/health.d.ts +9 -0
  43. package/dist/health.js +45 -0
  44. package/dist/index.d.ts +10 -0
  45. package/dist/index.js +141 -0
  46. package/dist/policy-provider.d.ts +3 -0
  47. package/dist/policy-provider.js +66 -0
  48. package/dist/publication-support.d.ts +14 -0
  49. package/dist/publication-support.js +69 -0
  50. package/dist/publication.d.ts +32 -0
  51. package/dist/publication.js +333 -0
  52. package/dist/receipt-statistics.d.ts +11 -0
  53. package/dist/receipt-statistics.js +58 -0
  54. package/dist/records.d.ts +299 -0
  55. package/dist/records.js +288 -0
  56. package/dist/repository-model.d.ts +54 -0
  57. package/dist/repository-model.js +132 -0
  58. package/dist/repository.d.ts +133 -0
  59. package/dist/repository.js +523 -0
  60. package/dist/resource-cursor.d.ts +5 -0
  61. package/dist/resource-cursor.js +45 -0
  62. package/dist/resource-presentation.d.ts +21 -0
  63. package/dist/resource-presentation.js +111 -0
  64. package/dist/resource-validation.d.ts +6 -0
  65. package/dist/resource-validation.js +80 -0
  66. package/dist/resources.d.ts +4 -0
  67. package/dist/resources.js +319 -0
  68. package/dist/scanner-configuration.d.ts +10 -0
  69. package/dist/scanner-configuration.js +146 -0
  70. package/dist/scanner-provider.d.ts +5 -0
  71. package/dist/scanner-provider.js +310 -0
  72. package/dist/scanner-result-validation.d.ts +3 -0
  73. package/dist/scanner-result-validation.js +61 -0
  74. package/dist/settings-preview.d.ts +6 -0
  75. package/dist/settings-preview.js +84 -0
  76. package/manifest.json +1601 -0
  77. package/migrations/0001_automod_standard.sql +114 -0
  78. package/migrations/0002_automod_enhanced_receipts.sql +40 -0
  79. package/package.json +61 -0
@@ -0,0 +1,114 @@
1
+ CREATE TABLE IF NOT EXISTS automod_rules (
2
+ rule_id uuid PRIMARY KEY,
3
+ guild_id text NOT NULL CHECK (guild_id ~ '^[0-9]{17,20}$'),
4
+ name text NOT NULL CHECK (char_length(name) BETWEEN 1 AND 80),
5
+ name_key text NOT NULL CHECK (char_length(name_key) BETWEEN 1 AND 80),
6
+ category text NOT NULL CHECK (category IN ('low', 'medium', 'high', 'critical')),
7
+ rule_kind text NOT NULL CHECK (rule_kind IN ('keyword', 'keyword_preset', 'spam', 'mention_spam')),
8
+ status text NOT NULL CHECK (status IN ('draft', 'published', 'disabled', 'drifted', 'missing', 'review')),
9
+ document_json jsonb NOT NULL CHECK (jsonb_typeof(document_json) = 'object'),
10
+ native_rule_id text CHECK (native_rule_id IS NULL OR native_rule_id ~ '^[0-9]{17,20}$'),
11
+ native_fingerprint text CHECK (native_fingerprint IS NULL OR native_fingerprint ~ '^[a-f0-9]{64}$'),
12
+ operation_key text NOT NULL CHECK (char_length(operation_key) BETWEEN 1 AND 200),
13
+ configuration_revision text NOT NULL CHECK (char_length(configuration_revision) BETWEEN 1 AND 200),
14
+ revision integer NOT NULL CHECK (revision >= 1),
15
+ created_by_user_id text CHECK (created_by_user_id IS NULL OR created_by_user_id ~ '^[0-9]{17,20}$'),
16
+ updated_by_user_id text CHECK (updated_by_user_id IS NULL OR updated_by_user_id ~ '^[0-9]{17,20}$'),
17
+ created_at timestamptz NOT NULL,
18
+ updated_at timestamptz NOT NULL,
19
+ UNIQUE (guild_id, rule_id),
20
+ UNIQUE (guild_id, name_key),
21
+ UNIQUE (guild_id, native_rule_id),
22
+ CHECK (updated_at >= created_at),
23
+ CHECK ((native_rule_id IS NULL) = (native_fingerprint IS NULL))
24
+ );
25
+
26
+ CREATE INDEX IF NOT EXISTS automod_rules_guild_updated_idx
27
+ ON automod_rules (guild_id, updated_at DESC, rule_id DESC);
28
+ CREATE INDEX IF NOT EXISTS automod_rules_guild_status_idx
29
+ ON automod_rules (guild_id, status, updated_at DESC, rule_id DESC);
30
+
31
+ CREATE TABLE IF NOT EXISTS automod_enforcement_claims (
32
+ claim_key text NOT NULL CHECK (claim_key ~ '^[a-f0-9]{64}$'),
33
+ guild_id text NOT NULL CHECK (guild_id ~ '^[0-9]{17,20}$'),
34
+ rule_id uuid NOT NULL,
35
+ rule_revision integer NOT NULL CHECK (rule_revision >= 1),
36
+ configuration_revision text NOT NULL CHECK (char_length(configuration_revision) BETWEEN 1 AND 200),
37
+ subject_user_id text CHECK (subject_user_id IS NULL OR subject_user_id ~ '^[0-9]{17,20}$'),
38
+ channel_id text CHECK (channel_id IS NULL OR channel_id ~ '^[0-9]{17,20}$'),
39
+ message_id text CHECK (message_id IS NULL OR message_id ~ '^[0-9]{17,20}$'),
40
+ category text NOT NULL CHECK (category IN ('low', 'medium', 'high', 'critical')),
41
+ action_family text NOT NULL CHECK (char_length(action_family) BETWEEN 1 AND 100),
42
+ source text NOT NULL CHECK (source IN ('native', 'enhanced')),
43
+ request_fingerprint text NOT NULL CHECK (request_fingerprint ~ '^[a-f0-9]{64}$'),
44
+ moderation_case_id uuid,
45
+ repeat_ordinal smallint CHECK (repeat_ordinal IS NULL OR repeat_ordinal BETWEEN 1 AND 3),
46
+ selected_action text CHECK (selected_action IS NULL OR selected_action IN ('case_only', 'delete_message', 'warn', 'timeout', 'kick', 'ban', 'demote')),
47
+ outcome text NOT NULL CHECK (outcome IN ('pending', 'applied', 'already_applied', 'native_only', 'rejected', 'failed', 'ambiguous', 'review_required')),
48
+ safe_code text CHECK (safe_code IS NULL OR char_length(safe_code) BETWEEN 1 AND 100),
49
+ revision integer NOT NULL CHECK (revision >= 1),
50
+ occurred_at timestamptz NOT NULL,
51
+ settled_at timestamptz,
52
+ retention_expires_at timestamptz NOT NULL,
53
+ created_at timestamptz NOT NULL,
54
+ updated_at timestamptz NOT NULL,
55
+ PRIMARY KEY (guild_id, claim_key),
56
+ FOREIGN KEY (guild_id, rule_id) REFERENCES automod_rules(guild_id, rule_id) ON DELETE RESTRICT,
57
+ CHECK (updated_at >= created_at),
58
+ CHECK ((settled_at IS NULL) = (outcome = 'pending')),
59
+ CHECK (retention_expires_at >= occurred_at + INTERVAL '90 days')
60
+ );
61
+
62
+ CREATE INDEX IF NOT EXISTS automod_claims_subject_rule_idx
63
+ ON automod_enforcement_claims (guild_id, subject_user_id, rule_id, occurred_at DESC)
64
+ WHERE subject_user_id IS NOT NULL;
65
+ CREATE INDEX IF NOT EXISTS automod_claims_retention_idx
66
+ ON automod_enforcement_claims (retention_expires_at, claim_key)
67
+ WHERE outcome <> 'pending';
68
+
69
+ CREATE TABLE IF NOT EXISTS automod_action_receipts (
70
+ receipt_id uuid PRIMARY KEY,
71
+ guild_id text NOT NULL CHECK (guild_id ~ '^[0-9]{17,20}$'),
72
+ event_key text NOT NULL CHECK (char_length(event_key) BETWEEN 1 AND 200),
73
+ rule_id uuid NOT NULL,
74
+ rule_revision integer NOT NULL CHECK (rule_revision >= 1),
75
+ configuration_revision text NOT NULL CHECK (char_length(configuration_revision) BETWEEN 1 AND 200),
76
+ native_rule_id text NOT NULL CHECK (native_rule_id ~ '^[0-9]{17,20}$'),
77
+ subject_user_id text CHECK (subject_user_id IS NULL OR subject_user_id ~ '^[0-9]{17,20}$'),
78
+ channel_id text CHECK (channel_id IS NULL OR channel_id ~ '^[0-9]{17,20}$'),
79
+ message_id text CHECK (message_id IS NULL OR message_id ~ '^[0-9]{17,20}$'),
80
+ alert_system_message_id text CHECK (alert_system_message_id IS NULL OR alert_system_message_id ~ '^[0-9]{17,20}$'),
81
+ action_type text NOT NULL CHECK (action_type IN ('block_message', 'send_alert_message', 'timeout')),
82
+ claim_key text NOT NULL CHECK (claim_key ~ '^[a-f0-9]{64}$'),
83
+ moderation_case_id uuid,
84
+ outcome text NOT NULL CHECK (outcome IN ('observed', 'applied', 'already_applied', 'native_only', 'rejected', 'failed', 'ambiguous', 'review_required')),
85
+ safe_code text CHECK (safe_code IS NULL OR char_length(safe_code) BETWEEN 1 AND 100),
86
+ occurred_at timestamptz NOT NULL,
87
+ retention_expires_at timestamptz NOT NULL,
88
+ created_at timestamptz NOT NULL,
89
+ UNIQUE (guild_id, event_key),
90
+ FOREIGN KEY (guild_id, rule_id) REFERENCES automod_rules(guild_id, rule_id) ON DELETE RESTRICT,
91
+ FOREIGN KEY (guild_id, claim_key) REFERENCES automod_enforcement_claims(guild_id, claim_key) DEFERRABLE INITIALLY DEFERRED,
92
+ CHECK (retention_expires_at >= occurred_at + INTERVAL '90 days')
93
+ );
94
+
95
+ CREATE INDEX IF NOT EXISTS automod_receipts_guild_occurred_idx
96
+ ON automod_action_receipts (guild_id, occurred_at DESC, receipt_id DESC);
97
+ CREATE INDEX IF NOT EXISTS automod_receipts_subject_idx
98
+ ON automod_action_receipts (guild_id, subject_user_id, occurred_at DESC)
99
+ WHERE subject_user_id IS NOT NULL;
100
+
101
+ CREATE TABLE IF NOT EXISTS automod_daily_counts (
102
+ guild_id text NOT NULL CHECK (guild_id ~ '^[0-9]{17,20}$'),
103
+ rule_id uuid NOT NULL,
104
+ day date NOT NULL,
105
+ source text NOT NULL CHECK (source IN ('native', 'enhanced')),
106
+ action_type text NOT NULL CHECK (char_length(action_type) BETWEEN 1 AND 50),
107
+ observed_count bigint NOT NULL DEFAULT 0 CHECK (observed_count >= 0),
108
+ last_observed_at timestamptz NOT NULL,
109
+ PRIMARY KEY (guild_id, rule_id, day, source, action_type),
110
+ FOREIGN KEY (guild_id, rule_id) REFERENCES automod_rules(guild_id, rule_id) ON DELETE RESTRICT
111
+ );
112
+
113
+ CREATE INDEX IF NOT EXISTS automod_daily_counts_day_idx
114
+ ON automod_daily_counts (day DESC, guild_id);
@@ -0,0 +1,40 @@
1
+ ALTER TABLE automod_action_receipts
2
+ ALTER COLUMN native_rule_id DROP NOT NULL;
3
+
4
+ ALTER TABLE automod_action_receipts
5
+ ADD COLUMN IF NOT EXISTS source text NOT NULL DEFAULT 'native',
6
+ ADD COLUMN IF NOT EXISTS detector_version text,
7
+ ADD COLUMN IF NOT EXISTS scoring_version text,
8
+ ADD COLUMN IF NOT EXISTS term_id text,
9
+ ADD COLUMN IF NOT EXISTS detection_method text,
10
+ ADD COLUMN IF NOT EXISTS confidence_class text,
11
+ ADD COLUMN IF NOT EXISTS confidence_score smallint,
12
+ ADD COLUMN IF NOT EXISTS effective_threshold smallint,
13
+ ADD COLUMN IF NOT EXISTS correlation_id uuid;
14
+
15
+ ALTER TABLE automod_action_receipts
16
+ DROP CONSTRAINT IF EXISTS automod_action_receipts_action_type_check;
17
+ ALTER TABLE automod_action_receipts
18
+ ADD CONSTRAINT automod_action_receipts_action_type_check
19
+ CHECK (action_type IN ('block_message', 'send_alert_message', 'timeout', 'detection'));
20
+
21
+ ALTER TABLE automod_action_receipts
22
+ ADD CONSTRAINT automod_action_receipts_source_check
23
+ CHECK (source IN ('native', 'enhanced')),
24
+ ADD CONSTRAINT automod_action_receipts_enhanced_shape_check
25
+ CHECK (
26
+ (source = 'native' AND action_type <> 'detection' AND native_rule_id IS NOT NULL) OR
27
+ (source = 'enhanced' AND action_type = 'detection' AND native_rule_id IS NULL AND
28
+ detector_version IS NOT NULL AND scoring_version IS NOT NULL AND
29
+ term_id IS NOT NULL AND detection_method IS NOT NULL AND
30
+ confidence_class IS NOT NULL AND confidence_score BETWEEN 0 AND 100 AND
31
+ effective_threshold BETWEEN 0 AND 100 AND correlation_id IS NOT NULL)
32
+ );
33
+
34
+ CREATE INDEX IF NOT EXISTS automod_receipts_case_idx
35
+ ON automod_action_receipts (guild_id, moderation_case_id)
36
+ WHERE moderation_case_id IS NOT NULL;
37
+
38
+ CREATE INDEX IF NOT EXISTS automod_claims_case_idx
39
+ ON automod_enforcement_claims (guild_id, moderation_case_id)
40
+ WHERE moderation_case_id IS NOT NULL;
package/package.json ADDED
@@ -0,0 +1,61 @@
1
+ {
2
+ "name": "@helyx/module-automod",
3
+ "version": "1.0.1",
4
+ "description": "Manage transparent Discord-native Auto Moderation rules and structural enforcement receipts.",
5
+ "keywords": [
6
+ "helyx",
7
+ "discord",
8
+ "auto-moderation",
9
+ "module"
10
+ ],
11
+ "private": false,
12
+ "license": "HSAL 1.0",
13
+ "homepage": "https://helyx.gg/modules/",
14
+ "bugs": {
15
+ "url": "https://github.com/ZyC0R3/Helyx/issues"
16
+ },
17
+ "repository": {
18
+ "type": "git",
19
+ "url": "git+https://github.com/ZyC0R3/Helyx.git",
20
+ "directory": "modules/automod"
21
+ },
22
+ "engines": {
23
+ "node": ">=24 <27",
24
+ "npm": ">=11"
25
+ },
26
+ "type": "module",
27
+ "publishConfig": {
28
+ "access": "public",
29
+ "provenance": true
30
+ },
31
+ "files": [
32
+ "dist",
33
+ "!dist/*.tsbuildinfo",
34
+ "!dist/**/*.map",
35
+ "migrations",
36
+ "manifest.json",
37
+ "README.md",
38
+ "CHANGELOG.md",
39
+ "LICENSE"
40
+ ],
41
+ "exports": {
42
+ ".": {
43
+ "types": "./dist/index.d.ts",
44
+ "default": "./dist/index.js"
45
+ },
46
+ "./engine": {
47
+ "types": "./dist/engine/index.d.ts",
48
+ "default": "./dist/engine/index.js"
49
+ },
50
+ "./package.json": "./package.json"
51
+ },
52
+ "scripts": {
53
+ "build": "tsc -b",
54
+ "test": "vitest run --root ../.. modules/automod/tests"
55
+ },
56
+ "dependencies": {
57
+ "@helyx/module-manifest": ">=0.11.0 <0.12.0",
58
+ "@helyx/sdk": ">=0.13.0 <0.14.0",
59
+ "zod": "4.4.3"
60
+ }
61
+ }