~singpolyma/biboumi

0ab5ecea133cef5a009bc34ba42c4eaacde6a7dd — Florent Le Coz 9 years ago 7bfe695
Cache the result of jidprep()

Avoid doing repetitive calculations, if we call jidprep() on the same JID multiple times
2 files changed, 20 insertions(+), 3 deletions(-)

M src/test.cpp
M src/xmpp/jid.cpp
M src/test.cpp => src/test.cpp +5 -0
@@ 288,7 288,12 @@ int main()
  // Jidprep
  const std::string& badjid("~zigougou™@EpiK-7D9D1FDE.poez.io/Boujour/coucou/slt™");
  const std::string correctjid = jidprep(badjid);
  std::cout << correctjid << std::endl;
  assert(correctjid == "~zigougoutm@epik-7d9d1fde.poez.io/Boujour/coucou/sltTM");
  // Check that the cache do not break things when we prep the same string
  // multiple times
  assert(jidprep(badjid) == "~zigougoutm@epik-7d9d1fde.poez.io/Boujour/coucou/sltTM");
  assert(jidprep(badjid) == "~zigougoutm@epik-7d9d1fde.poez.io/Boujour/coucou/sltTM");

  const std::string& badjid2("Zigougou@poez.io");
  const std::string correctjid2 = jidprep(badjid2);

M src/xmpp/jid.cpp => src/xmpp/jid.cpp +15 -3
@@ 1,6 1,7 @@
#include <xmpp/jid.hpp>
#include <config.h>
#include <cstring>
#include <map>

#ifdef LIBIDN_FOUND
 #include <stringprep.h>


@@ 35,7 36,14 @@ static constexpr size_t max_jid_part_len = 1023;
std::string jidprep(const std::string& original)
{
#ifdef LIBIDN_FOUND
  // TODO: cache the result
  using CacheType = std::map<std::string, std::string>;
  static CacheType cache;
  std::pair<CacheType::iterator, bool> cached = cache.insert({original, {}});
  if (std::get<1>(cached) == false)
    { // Insertion failed: the result is already in the cache, return it
      return std::get<0>(cached)->second;
    }

  const std::string error_msg("Failed to convert " + original + " into a valid JID:");
  Jid jid(original);



@@ 61,7 69,10 @@ std::string jidprep(const std::string& original)

  // If there is no resource, stop here
  if (jid.resource.empty())
    return std::string(local) + "@" + domain;
    {
      std::get<0>(cached)->second = std::string(local) + "@" + domain;
      return std::get<0>(cached)->second;
    }

  // Otherwise, also process the resource part
  char resource[max_jid_part_len] = {};


@@ 73,7 84,8 @@ std::string jidprep(const std::string& original)
      log_error(error_msg + stringprep_strerror(rc));
      return "";
    }
  return std::string(local) + "@" + domain + "/" + resource;
  std::get<0>(cached)->second = std::string(local) + "@" + domain + "/" + resource;
  return std::get<0>(cached)->second;

#else
  (void)original;