diff options
| author | tanaka takashi <isazaka@gmail.com> | 2026-07-04 14:54:45 +0900 |
|---|---|---|
| committer | tanaka takashi <isazaka@gmail.com> | 2026-07-04 14:54:45 +0900 |
| commit | 1efecaef1f867cb218366e2b4ab4b901fdd2835f (patch) | |
| tree | 3080a3d80a1a0671e8e82819d3f785465aace162 /src/domain/message.c | |
| parent | 34e00404e9561dcaf8d2d99df7470757a4fee915 (diff) | |
途中経過コミット
Diffstat (limited to 'src/domain/message.c')
| -rw-r--r-- | src/domain/message.c | 176 |
1 files changed, 174 insertions, 2 deletions
diff --git a/src/domain/message.c b/src/domain/message.c index b1db3e1..ec019c4 100644 --- a/src/domain/message.c +++ b/src/domain/message.c @@ -33,6 +33,9 @@ tiny_message_init(tiny_message_t *message) } memset(message, 0, sizeof(*message)); message->metadata.memory_tier = TINY_TIER_SHORT; + message->metadata.memory_kind = TINY_KIND_CONVERSATION; + message->metadata.importance = 50; + message->revision = 1; } void @@ -46,11 +49,18 @@ tiny_message_free(tiny_message_t *message) free(message->session_id); free(message->content); free(message->metadata.tool_call_id); + free(message->metadata.summary); for (index = 0; index < message->metadata.tag_count; ++index) { free(message->metadata.tags[index]); } free(message->metadata.tags); + free(message->metadata.relations); + for (index = 0; index < message->metadata.source_count; ++index) + { + free(message->metadata.source_message_ids[index]); + } + free(message->metadata.source_message_ids); tiny_message_init(message); } @@ -59,8 +69,7 @@ tiny_message_copy(tiny_message_t *destination, const tiny_message_t *source) { size_t index; if (destination == NULL || source == NULL || destination == source || source->session_id == NULL - || source->content == NULL - || (source->metadata.tag_count != 0 && source->metadata.tags == NULL)) + || source->content == NULL || !tiny_metadata_valid(&source->metadata)) { return -1; } @@ -69,12 +78,56 @@ tiny_message_copy(tiny_message_t *destination, const tiny_message_t *source) destination->timestamp_ms = source->timestamp_ms; destination->role = source->role; destination->metadata.memory_tier = source->metadata.memory_tier; + destination->metadata.memory_kind = source->metadata.memory_kind; + destination->metadata.importance = source->metadata.importance; + destination->revision = source->revision; + destination->updated_at_ms = source->updated_at_ms; destination->session_id = duplicate_string(source->session_id); destination->content = duplicate_string(source->content); if (destination->session_id == NULL || destination->content == NULL) { return copy_failed(destination); } + if (source->metadata.summary != NULL) + { + destination->metadata.summary = duplicate_string(source->metadata.summary); + if (destination->metadata.summary == NULL) + { + return copy_failed(destination); + } + } + if (source->metadata.relation_count > 0) + { + destination->metadata.relations + = malloc(source->metadata.relation_count * sizeof(*destination->metadata.relations)); + if (destination->metadata.relations == NULL) + { + return copy_failed(destination); + } + memcpy(destination->metadata.relations, + source->metadata.relations, + source->metadata.relation_count * sizeof(*destination->metadata.relations)); + destination->metadata.relation_count = source->metadata.relation_count; + } + if (source->metadata.source_count > 0) + { + destination->metadata.source_message_ids + = calloc(source->metadata.source_count, sizeof(char *)); + if (destination->metadata.source_message_ids == NULL) + { + return copy_failed(destination); + } + for (index = 0; index < source->metadata.source_count; ++index) + { + destination->metadata.source_message_ids[index] + = duplicate_string(source->metadata.source_message_ids[index]); + if (destination->metadata.source_message_ids[index] == NULL) + { + return copy_failed(destination); + } + destination->metadata.source_count++; + } + } if (source->metadata.tool_call_id != NULL) { destination->metadata.tool_call_id = duplicate_string(source->metadata.tool_call_id); @@ -103,6 +156,70 @@ tiny_message_copy(tiny_message_t *destination, const tiny_message_t *source) return 0; } +bool +tiny_metadata_valid(const tiny_metadata_t *metadata) +{ + size_t index, other; + if (!metadata || metadata->memory_tier < TINY_TIER_SHORT + || metadata->memory_tier > TINY_TIER_DISCARD || metadata->memory_kind < TINY_KIND_CONVERSATION + || metadata->memory_kind > TINY_KIND_SUMMARY || metadata->importance > 100 + || metadata->tag_count > TINY_TAG_COUNT_MAX || (metadata->tag_count && !metadata->tags) + || metadata->relation_count > TINY_RELATION_COUNT_MAX + || (metadata->relation_count && !metadata->relations) + || metadata->source_count > TINY_SOURCE_COUNT_MAX + || (metadata->source_count && !metadata->source_message_ids)) + { + return false; + } + if (metadata->summary + && (strlen(metadata->summary) > TINY_SUMMARY_MAX + || !tiny_utf8_valid(metadata->summary, strlen(metadata->summary)))) + { + return false; + } + for (index = 0; index < metadata->tag_count; ++index) + { + if (!metadata->tags[index] || !metadata->tags[index][0] + || strlen(metadata->tags[index]) > TINY_TAG_MAX) + { + return false; + } + } + for (index = 0; index < metadata->relation_count; ++index) + { + const tiny_relation_t *relation = &metadata->relations[index]; + if (relation->type < TINY_RELATION_DEPENDS_ON || relation->type > TINY_RELATION_RELATED_TO + || !tiny_message_id_valid(relation->message_id)) + { + return false; + } + for (other = 0; other < index; ++other) + { + if (relation->type == metadata->relations[other].type + && strcmp(relation->message_id, metadata->relations[other].message_id) == 0) + { + return false; + } + } + } + for (index = 0; index < metadata->source_count; ++index) + { + if (!metadata->source_message_ids[index] + || !tiny_message_id_valid(metadata->source_message_ids[index])) + { + return false; + } + for (other = 0; other < index; ++other) + { + if (strcmp(metadata->source_message_ids[index], metadata->source_message_ids[other]) == 0) + { + return false; + } + } + } + return true; +} + const char * tiny_role_name(tiny_role_t role) { @@ -193,6 +310,61 @@ tiny_tier_parse(const char *value, tiny_memory_tier_t *tier) return true; } +const char * +tiny_kind_name(tiny_memory_kind_t kind) +{ + static const char *names[] + = { "unknown", "conversation", "episode", "semantic", "procedure", "preference", "summary" }; + return kind >= TINY_KIND_CONVERSATION && kind <= TINY_KIND_SUMMARY ? names[kind] : names[0]; +} + +bool +tiny_kind_parse(const char *value, tiny_memory_kind_t *kind) +{ + tiny_memory_kind_t candidate; + if (value == NULL || kind == NULL) + { + return false; + } + for (candidate = TINY_KIND_CONVERSATION; candidate <= TINY_KIND_SUMMARY; ++candidate) + { + if (strcmp(value, tiny_kind_name(candidate)) == 0) + { + *kind = candidate; + return true; + } + } + return false; +} + +const char * +tiny_relation_type_name(tiny_relation_type_t type) +{ + static const char *names[] + = { "unknown", "depends_on", "derived_from", "supersedes", "related_to" }; + return type >= TINY_RELATION_DEPENDS_ON && type <= TINY_RELATION_RELATED_TO ? names[type] + : names[0]; +} + +bool +tiny_relation_type_parse(const char *value, tiny_relation_type_t *type) +{ + tiny_relation_type_t candidate; + if (value == NULL || type == NULL) + { + return false; + } + for (candidate = TINY_RELATION_DEPENDS_ON; candidate <= TINY_RELATION_RELATED_TO; ++candidate) + { + if (strcmp(value, tiny_relation_type_name(candidate)) == 0) + { + *type = candidate; + return true; + } + } + return false; +} + bool tiny_utf8_valid(const char *value, size_t length) { |
