<commit_before>/* Copyright (c) 2006-2011 Dovecot authors, see the included COPYING file */

#include "lib.h"
#include "array.h"
#include "hex-binary.h"
#include "mail-index.h"
#include "mail-storage-private.h"
#include "mail-search.h"
#include "../virtual/virtual-storage.h"
#include "fts-api-private.h"

static ARRAY_DEFINE(backends, const struct fts_backend *);

void fts_backend_register(const struct fts_backend *backend)
{
	if (!array_is_created(&backends))
		i_array_init(&backends, 4);
	array_append(&backends, &backend, 1);
}

void fts_backend_unregister(const char *name)
{
	const struct fts_backend *const *be;
	unsigned int i, count;

	be = array_get(&backends, &count);
	for (i = 0; i < count; i++) {
		if (strcmp(be[i]->name, name) == 0) {
			array_delete(&backends, i, 1);
			break;
		}
	}
	if (i == count)
		i_panic("fts_backend_unregister(%s): unknown backend", name);

	if (count == 1)
		array_free(&backends);
}

static const struct fts_backend *
fts_backend_class_lookup(const char *backend_name)
{
	const struct fts_backend *const *be;
	unsigned int i, count;

	if (array_is_created(&backends)) {
		be = array_get(&backends, &count);
		for (i = 0; i < count; i++) {
			if (strcmp(be[i]->name, backend_name) == 0)
				return be[i];
		}
	}
	return NULL;
}

int fts_backend_init(const char *backend_name, struct mail_namespace *ns,
		     const char **error_r, struct fts_backend **backend_r)
{
	const struct fts_backend *be;
	struct fts_backend *backend;

	be = fts_backend_class_lookup(backend_name);
	if (be == NULL) {
		*error_r = "Unknown backend";
		return -1;
	}

	backend = be->v.alloc();
	backend->ns = ns;
	if (backend->v.init(backend, error_r) < 0) {
		i_free(backend);
		return -1;
	}
	*backend_r = backend;
	return 0;
}

void fts_backend_deinit(struct fts_backend **_backend)
{
	struct fts_backend *backend = *_backend;

	*_backend = NULL;
	backend->v.deinit(backend);
}

int fts_backend_get_last_uid(struct fts_backend *backend, struct mailbox *box,
			     uint32_t *last_uid_r)
{
	if (strcmp(box->storage->name, VIRTUAL_STORAGE_NAME) == 0) {
		/* virtual mailboxes themselves don't have any indexes,
		   so catch this call here */
		if (!fts_index_get_last_uid(box, last_uid_r))
			*last_uid_r = 0;
		return 0;
	}

	return backend->v.get_last_uid(backend, box, last_uid_r);
}

bool fts_backend_is_updating(struct fts_backend *backend)
{
	return backend->updating;
}

struct fts_backend_update_context *
fts_backend_update_init(struct fts_backend *backend)
{
	i_assert(!backend->updating);

	backend->updating = TRUE;
	return backend->v.update_init(backend);
}

static void fts_backend_set_cur_mailbox(struct fts_backend_update_context *ctx)
{
	fts_backend_update_unset_build_key(ctx);
	if (ctx->backend_box != ctx->cur_box) {
		ctx->backend->v.update_set_mailbox(ctx, ctx->cur_box);
		ctx->backend_box = ctx->cur_box;
	}
}

int fts_backend_update_deinit(struct fts_backend_update_context **_ctx)
{
	struct fts_backend_update_context *ctx = *_ctx;

	*_ctx = NULL;

	ctx->cur_box = NULL;
	fts_backend_set_cur_mailbox(ctx);

	return ctx->backend->v.update_deinit(ctx);
}

void fts_backend_update_set_mailbox(struct fts_backend_update_context *ctx,
				    struct mailbox *box)
{
	if (ctx->backend_box != NULL && box != ctx->backend_box) {
		/* make sure we don't reference the backend box anymore */
		ctx->backend->v.update_set_mailbox(ctx, NULL);
		ctx->backend_box = NULL;
	}
	ctx->cur_box = box;
}

void fts_backend_update_expunge(struct fts_backend_update_context *ctx,
				uint32_t uid)
{
	fts_backend_set_cur_mailbox(ctx);<commit_msg>fts: Clear updating flag on update deinit.<commit_after>/* Copyright (c) 2006-2011 Dovecot authors, see the included COPYING file */

#include "lib.h"
#include "array.h"
#include "hex-binary.h"
#include "mail-index.h"
#include "mail-storage-private.h"
#include "mail-search.h"
#include "../virtual/virtual-storage.h"
#include "fts-api-private.h"

static ARRAY_DEFINE(backends, const struct fts_backend *);

void fts_backend_register(const struct fts_backend *backend)
{
	if (!array_is_created(&backends))
		i_array_init(&backends, 4);
	array_append(&backends, &backend, 1);
}

void fts_backend_unregister(const char *name)
{
	const struct fts_backend *const *be;
	unsigned int i, count;

	be = array_get(&backends, &count);
	for (i = 0; i < count; i++) {
		if (strcmp(be[i]->name, name) == 0) {
			array_delete(&backends, i, 1);
			break;
		}
	}
	if (i == count)
		i_panic("fts_backend_unregister(%s): unknown backend", name);

	if (count == 1)
		array_free(&backends);
}

static const struct fts_backend *
fts_backend_class_lookup(const char *backend_name)
{
	const struct fts_backend *const *be;
	unsigned int i, count;

	if (array_is_created(&backends)) {
		be = array_get(&backends, &count);
		for (i = 0; i < count; i++) {
			if (strcmp(be[i]->name, backend_name) == 0)
				return be[i];
		}
	}
	return NULL;
}

int fts_backend_init(const char *backend_name, struct mail_namespace *ns,
		     const char **error_r, struct fts_backend **backend_r)
{
	const struct fts_backend *be;
	struct fts_backend *backend;

	be = fts_backend_class_lookup(backend_name);
	if (be == NULL) {
		*error_r = "Unknown backend";
		return -1;
	}

	backend = be->v.alloc();
	backend->ns = ns;
	if (backend->v.init(backend, error_r) < 0) {
		i_free(backend);
		return -1;
	}
	*backend_r = backend;
	return 0;
}

void fts_backend_deinit(struct fts_backend **_backend)
{
	struct fts_backend *backend = *_backend;

	*_backend = NULL;
	backend->v.deinit(backend);
}

int fts_backend_get_last_uid(struct fts_backend *backend, struct mailbox *box,
			     uint32_t *last_uid_r)
{
	if (strcmp(box->storage->name, VIRTUAL_STORAGE_NAME) == 0) {
		/* virtual mailboxes themselves don't have any indexes,
		   so catch this call here */
		if (!fts_index_get_last_uid(box, last_uid_r))
			*last_uid_r = 0;
		return 0;
	}

	return backend->v.get_last_uid(backend, box, last_uid_r);
}

bool fts_backend_is_updating(struct fts_backend *backend)
{
	return backend->updating;
}

struct fts_backend_update_context *
fts_backend_update_init(struct fts_backend *backend)
{
	i_assert(!backend->updating);

	backend->updating = TRUE;
	return backend->v.update_init(backend);
}

static void fts_backend_set_cur_mailbox(struct fts_backend_update_context *ctx)
{
	fts_backend_update_unset_build_key(ctx);
	if (ctx->backend_box != ctx->cur_box) {
		ctx->backend->v.update_set_mailbox(ctx, ctx->cur_box);
		ctx->backend_box = ctx->cur_box;
	}
}

int fts_backend_update_deinit(struct fts_backend_update_context **_ctx)
{
	struct fts_backend_update_context *ctx = *_ctx;
	struct fts_backend *backend = ctx->backend;
	int ret;

	*_ctx = NULL;

	ctx->cur_box = NULL;
	fts_backend_set_cur_mailbox(ctx);

	ret = backend->v.update_deinit(ctx);
	backend->updating = FALSE;
	return ret;
}

void fts_backend_update_set_mailbox(struct fts_backend_update_context *ctx,
				    struct mailbox *box)
{
	if (ctx->backend_box != NULL && box != ctx->backend_box) {
		/* make sure we don't reference the backend box anymore */
		ctx->backend->v.update_set_mailbox(ctx, NULL);
		ctx->backend_box = NULL;
	}
	ctx->cur_box = box;
}

void fts_backend_update_expunge(struct fts_backend_update_context *ctx,
				uint32_t uid)
{
	fts_backend_set_cur_mailbox(ctx);
{'fraction_non_alphanumeric': 0.13269098417068134, 'fraction_numerical': 0.007432897453544391, 'mean_word_length': 4.9655172413793105, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 62, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4860887', 'n_tokens_mistral': 2906, 'n_tokens_neox': 2724, 'n_words': 595}