atomic_bool running = true;

#define PORT 8000
#define PREFIX "/api"

int callback_default(const struct _u_request *request, struct _u_response *response, void *user_data);
int callback_all_test_foo(const struct _u_request *request, struct _u_response *response, void *user_data);

void *thread_server(void *vargp) {
  int ret;
  struct _u_instance instance;

  if (ulfius_init_instance(&instance, PORT, NULL, NULL) != U_OK) {
    exit(1);
  }

  instance.max_post_body_size = 1024;

  ulfius_add_endpoint_by_val(&instance, "GET", PREFIX, "/param/:name", 0, &callback_all_test_foo, "user data 1");
  ulfius_add_endpoint_by_val(&instance, "POST", PREFIX, "/param/:name", 0, &callback_all_test_foo, "user data 2");

  ulfius_set_default_endpoint(&instance, &callback_default, NULL);

  ret = ulfius_start_framework(&instance);

  if (ret == U_OK) {
    printf("Server started at %d.\n", PORT);
  } else {
    printf("Error starting server as %d port.\n", PORT);
  }

  while (running) {
  }
  printf("Server halt.\n");

  ulfius_stop_framework(&instance);
  ulfius_clean_instance(&instance);
}

int callback_default(const struct _u_request *request, struct _u_response *response, void *user_data) {
  (void)(request);
  (void)(user_data);
  ulfius_set_string_body_response(response, 404, "Page not found, do what you want");

  return U_CALLBACK_CONTINUE;
}

int callback_all_test_foo(const struct _u_request *request, struct _u_response *response, void *user_data) {
  // url_params = request->map_url
  // post_params = request->map_post_body

  const char **keys, *value;
  keys = u_map_enum_keys(request->map_url);
  value = u_map_get(request->map_url, keys[0]);

  if (strcmp("quit", value) == 0) {
    running = false;
  }

  char *response_body = msprintf("Your %s is %s\n", keys[0], value);

  print_to_terminal(response_body);
  ulfius_set_string_body_response(response, 200, response_body);

  o_free(response_body);

  return U_CALLBACK_CONTINUE;
}
