bcb4e51a409d94ae670de96afb8483a4f7855294Stephan Bosch/* Copyright (c) 2015-2018 Dovecot authors, see the included COPYING file */
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "lib.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "str.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "fts-language.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "fts-filter-private.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "fts-common.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila#include "unichar.h"
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilastatic int
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilafts_filter_contractions_create(const struct fts_language *lang,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila const char *const *settings,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila struct fts_filter **filter_r,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila const char **error_r)
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila{
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila struct fts_filter *filter;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (settings[0] != NULL) {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila *error_r = t_strdup_printf("Unknown setting: %s", settings[0]);
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila return -1;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila }
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (strcmp(lang->name, "fr") != 0) {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila *error_r = t_strdup_printf("Unsupported language: %s", lang->name);
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila return -1;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila }
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila filter = i_new(struct fts_filter, 1);
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila *filter = *fts_filter_contractions;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila filter->token = str_new(default_pool, 64);
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila *filter_r = filter;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila return 0;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila}
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilastatic int
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilafts_filter_contractions_filter(struct fts_filter *filter ATTR_UNUSED,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila const char **_token,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila const char **error_r ATTR_UNUSED)
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila{
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila int char_size, pos = 0;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila unichar_t apostrophe;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila const char *token = *_token;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila switch (token[pos]) {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'q':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila pos++;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (token[pos] == '\0' || token[pos] != 'u')
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila break;
f784d5bb8edbec88829524135cfa100129f5384dTimo Sirainen /* fall through */
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'c':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'd':
87af299c8a8bbca798a479896f361163c9539437Teemu Huovila case 'j':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'l':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'm':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 'n':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 's':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila case 't':
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila pos++;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (token[pos] == '\0')
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila break;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila char_size = uni_utf8_get_char(token + pos, &apostrophe);
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (IS_APOSTROPHE(apostrophe)) {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila pos += char_size;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila *_token = token + pos;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila }
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila if (token[pos] == '\0') /* nothing left */
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila return 0;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila break;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila default:
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila /* do nothing */
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila break;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila }
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila return 1;
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila}
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilastatic const struct fts_filter fts_filter_contractions_real = {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila .class_name = "contractions",
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila .v = {
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila fts_filter_contractions_create,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila fts_filter_contractions_filter,
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila NULL
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila }
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila};
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovila
440b625484f3cc9d3ec0a7ba36fe3583aa90172dTeemu Huovilaconst struct fts_filter *fts_filter_contractions = &fts_filter_contractions_real;