refactor: block fallback options

This commit is contained in:
Mohamed Marrouchi 2025-06-12 11:34:17 +01:00
parent 4e1d461ddb
commit b9acf9d0c7
6 changed files with 73 additions and 29 deletions

View File

@ -0,0 +1,17 @@
/*
* Copyright © 2025 Hexastack. All rights reserved.
*
* Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms:
* 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission.
* 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file).
*/
import { FallbackOptions } from '../schemas/types/options';
export function getDefaultFallbackOptions(): FallbackOptions {
return {
active: false,
max_attempts: 0,
message: [],
};
}

View File

@ -0,0 +1,28 @@
/*
* Copyright © 2025 Hexastack. All rights reserved.
*
* Licensed under the GNU Affero General Public License v3.0 (AGPLv3) with the following additional terms:
* 1. The name "Hexabot" is a trademark of Hexastack. You may not use this name in derivative works without express written permission.
* 2. All derivative works must include clear attribution to the original creator and software, Hexastack and Hexabot, in a prominent location (e.g., in the software's "About" section, documentation, and README file).
*/
import { Subscriber } from '../schemas/subscriber.schema';
import { Context } from '../schemas/types/context';
export function getDefaultConversationContext(): Context {
return {
vars: {}, // Used for capturing vars from user entries
user: {
first_name: '',
last_name: '',
// @TODO: Typing is not correct
} as Subscriber,
user_location: {
// Used for capturing geolocation from QR
lat: 0.0,
lon: 0.0,
},
skip: {}, // Used for list pagination
attempt: 0, // Used to track fallback max attempts
};
}

View File

@ -17,27 +17,12 @@ import {
THydratedDocument,
} from '@/utils/types/filter.types';
import { getDefaultConversationContext } from '../constants/conversation';
import { Block } from './block.schema';
import { Subscriber } from './subscriber.schema';
import { Context } from './types/context';
export function getDefaultConversationContext(): Context {
return {
vars: {}, // Used for capturing vars from user entries
user: {
first_name: '',
last_name: '',
} as Subscriber,
user_location: {
// Used for capturing geolocation from QR
lat: 0.0,
lon: 0.0,
},
skip: {}, // Used for list pagination
attempt: 0, // Used to track fallback max attempts
};
}
@Schema({ timestamps: true, minimize: false })
class ConversationStub extends BaseSchema {
@Prop({

View File

@ -29,16 +29,18 @@ export const contentOptionsSchema = z.object({
export type ContentOptions = z.infer<typeof contentOptionsSchema>;
export const fallbackOptionsSchema = z.object({
active: z.boolean(),
message: z.array(z.string()),
max_attempts: z.number().finite(),
});
export type FallbackOptions = z.infer<typeof fallbackOptionsSchema>;
export const BlockOptionsSchema = z.object({
typing: z.number().optional(),
content: contentOptionsSchema.optional(),
fallback: z
.object({
active: z.boolean(),
message: z.array(z.string()),
max_attempts: z.number().finite(),
})
.optional(),
fallback: fallbackOptionsSchema.optional(),
assignTo: z.string().optional(),
effects: z.array(z.string()).optional(),
});

View File

@ -23,6 +23,7 @@ import { FALLBACK_DEFAULT_NLU_PENALTY_FACTOR } from '@/utils/constants/nlp';
import { BaseService } from '@/utils/generics/base-service';
import { getRandomElement } from '@/utils/helpers/safeRandom';
import { getDefaultFallbackOptions } from '../constants/block';
import { BlockDto } from '../dto/block.dto';
import { EnvelopeFactory } from '../helpers/envelope-factory';
import { BlockRepository } from '../repositories/block.repository';
@ -40,6 +41,7 @@ import {
StdOutgoingEnvelope,
StdOutgoingSystemEnvelope,
} from '../schemas/types/message';
import { FallbackOptions } from '../schemas/types/options';
import { NlpPattern, PayloadPattern } from '../schemas/types/pattern';
import { Payload } from '../schemas/types/quick-reply';
import { SubscriberContext } from '../schemas/types/subscriberContext';
@ -775,6 +777,19 @@ export class BlockService extends BaseService<
throw new Error('Invalid message format.');
}
/**
* Retrieves the fallback options for a block.
*
* @param block - The block to retrieve fallback options from.
* @returns The fallback options for the block, or default options if not specified.
*/
getFallbackOptions<T extends BlockStub>(block: T): FallbackOptions {
const fallbackOptions: FallbackOptions = block.options?.fallback
? block.options.fallback
: getDefaultFallbackOptions();
return fallbackOptions;
}
/**
* Updates the `trigger_labels` and `assign_labels` fields of a block when a label is deleted.
*

View File

@ -14,13 +14,10 @@ import EventWrapper from '@/channel/lib/EventWrapper';
import { LoggerService } from '@/logger/logger.service';
import { SettingService } from '@/setting/services/setting.service';
import { getDefaultConversationContext } from '../constants/conversation';
import { MessageCreateDto } from '../dto/message.dto';
import { BlockFull } from '../schemas/block.schema';
import {
Conversation,
ConversationFull,
getDefaultConversationContext,
} from '../schemas/conversation.schema';
import { Conversation, ConversationFull } from '../schemas/conversation.schema';
import { Context } from '../schemas/types/context';
import {
IncomingMessageType,