feat: Static segments

This commit is contained in:
Dries Augustyns
2026-02-23 13:57:32 +01:00
parent 21af8fe05e
commit 4b51e386e3
10 changed files with 664 additions and 87 deletions
@@ -0,0 +1,6 @@
-- CreateEnum
CREATE TYPE "SegmentType" AS ENUM ('DYNAMIC', 'STATIC');
-- AlterTable
ALTER TABLE "segments" ADD COLUMN "type" "SegmentType" NOT NULL DEFAULT 'DYNAMIC',
ALTER COLUMN "condition" DROP NOT NULL;
+10 -2
View File
@@ -199,8 +199,11 @@ model Segment {
name String
description String?
// Filter condition (evaluated dynamically)
condition Json
// Segment type: DYNAMIC (filter-based) or STATIC (manually managed)
type SegmentType @default(DYNAMIC)
// Filter condition (evaluated dynamically, null for STATIC segments)
condition Json?
// Nested filter structure with AND/OR logic:
// {
// logic: "OR",
@@ -747,6 +750,11 @@ enum StepExecutionStatus {
FAILED // Failed with error
}
enum SegmentType {
DYNAMIC // Filter-based segment evaluated against contacts at query time
STATIC // Manually curated list of contacts managed via memberships
}
enum EmailSourceType {
TRANSACTIONAL // Sent via API call
CAMPAIGN // Sent as part of broadcast
+6 -1
View File
@@ -132,15 +132,20 @@ export const SegmentSchemas = {
create: z.object({
name: z.string().min(1).max(100),
description: z.string().max(500).optional(),
condition: filterConditionSchema,
type: z.enum(['DYNAMIC', 'STATIC']).default('DYNAMIC'),
condition: filterConditionSchema.optional(),
trackMembership: z.boolean().default(false),
}),
update: z.object({
name: z.string().min(1).max(100).optional(),
description: z.string().max(500).optional(),
type: z.enum(['DYNAMIC', 'STATIC']).optional(),
condition: filterConditionSchema.optional(),
trackMembership: z.boolean().optional(),
}),
members: z.object({
emails: z.array(z.string().email()).min(1).max(500),
}),
};
export const TemplateSchemas = {
+5 -1
View File
@@ -2,6 +2,8 @@
* Segment and filter types
*/
export type SegmentType = 'DYNAMIC' | 'STATIC';
// Segment filter types
export type SegmentFilterOperator =
// Standard operators (for contact fields)
@@ -45,13 +47,15 @@ export interface FilterCondition {
export interface CreateSegmentData {
name: string;
description?: string;
condition: FilterCondition;
type?: SegmentType;
condition?: FilterCondition;
trackMembership?: boolean;
}
export interface UpdateSegmentData {
name?: string;
description?: string;
type?: SegmentType;
condition?: FilterCondition;
trackMembership?: boolean;
}