aboutsummaryrefslogtreecommitdiff
path: root/src/Main.c
blob: 988d0b03a7bc987fad4931eb87b31a8ef2794b43 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
#include <beaker.h>
#include <curl/curl.h>
#include <libxml/parser.h>
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>

#include "Cache/Cache.h"
#include "Config.h"
#include "Infobox/Wikipedia.h"
#include "Proxy/Proxy.h"
#include "Routes/Home.h"
#include "Routes/ImageProxy.h"
#include "Routes/Images.h"
#include "Routes/Search.h"
#include "Routes/Settings.h"
#include "Routes/SettingsSave.h"
#include "Scraping/Scraping.h"

Config global_config;
 
int handle_opensearch(UrlParams *params) {
  (void)params;
  extern Config global_config;
  TemplateContext ctx = new_context();
  context_set(&ctx, "domain", global_config.domain);
  char *rendered = render_template("opensearch.xml", &ctx);
  serve_data(rendered, strlen(rendered), "application/opensearchdescription+xml");

  free(rendered);
  free_context(&ctx);
  return 0;
}

int main() {
  sigset_t mask;
  sigemptyset(&mask);
  sigaddset(&mask, SIGPIPE);
  pthread_sigmask(SIG_BLOCK, &mask, NULL);

  LIBXML_TEST_VERSION
  xmlInitParser();

  curl_global_init(CURL_GLOBAL_DEFAULT);

  Config cfg = {.host = DEFAULT_HOST,
                .port = DEFAULT_PORT,
                .domain = "",
                .proxy = "",
                .proxy_list_file = "",
                .max_proxy_retries = DEFAULT_MAX_PROXY_RETRIES,
                .randomize_username = 0,
                .randomize_password = 0,
                .cache_dir = DEFAULT_CACHE_DIR,
                .cache_ttl_search = DEFAULT_CACHE_TTL_SEARCH,
                .cache_ttl_infobox = DEFAULT_CACHE_TTL_INFOBOX,
                .cache_ttl_image = DEFAULT_CACHE_TTL_IMAGE,
                .engines = "",
                .rate_limit_search_requests = 0,
                .rate_limit_search_interval = 0,
                .rate_limit_images_requests = 0,
                .rate_limit_images_interval = 0};

  if (load_config("config.ini", &cfg) != 0) {
    fprintf(stderr, "[WARN] Could not load config file, using defaults\n");
  }

  global_config = cfg;

  int loaded = beaker_load_locales();
  if (loaded > 0) {
    fprintf(stderr, "[INFO] Loaded %d locales\n", loaded);
  } else {
    fprintf(stderr, "[WARN] No locales loaded (make sure to run from omnisearch directory)\n");
  }

  apply_engines_config(cfg.engines);

  if (cache_init(cfg.cache_dir) != 0) {
    fprintf(stderr,
            "[WARN] Failed to initialize cache, continuing without caching\n");
  } else {
    fprintf(stderr, "[INFO] Cache initialized at %s\n", cfg.cache_dir);
    cache_cleanup(cfg.cache_ttl_search);
  }

  set_cache_ttl_search(cfg.cache_ttl_search);
  set_cache_ttl_infobox(cfg.cache_ttl_infobox);
  set_cache_ttl_image(cfg.cache_ttl_image);

  if (cfg.proxy_list_file[0] != '\0') {
    if (load_proxy_list(cfg.proxy_list_file) < 0) {
      fprintf(stderr,
              "[WARN] Failed to load proxy list, continuing without proxies\n");
    }
  }

  max_proxy_retries = cfg.max_proxy_retries;
  set_proxy_config(cfg.proxy, cfg.randomize_username, cfg.randomize_password);

  if (proxy_url[0] != '\0') {
    fprintf(stderr, "[INFO] Using proxy: %s\n", proxy_url);
  } else if (proxy_count > 0) {
    fprintf(stderr, "[INFO] Using %d proxies from %s\n", proxy_count,
            cfg.proxy_list_file);
  }

  set_handler("/", home_handler);
  set_handler("/opensearch.xml", handle_opensearch);
  set_handler("/search", results_handler);
  set_handler("/images", images_handler);
  set_handler("/proxy", image_proxy_handler);
  set_handler("/settings", settings_handler);
  set_handler("/save_settings", settings_save_handler);

  fprintf(stderr, "[INFO] Starting Omnisearch on %s:%d\n", cfg.host, cfg.port);

  int result = beaker_run(cfg.host, cfg.port);

  if (result != 0) {
    fprintf(stderr, "[ERROR] Beaker server failed to start.\n");
    curl_global_cleanup();
    xmlCleanupParser();
    return EXIT_FAILURE;
  }

  curl_global_cleanup();
  xmlCleanupParser();
  beaker_free_locales();
  free_proxy_list();
  cache_shutdown();
  return EXIT_SUCCESS;
}