<commit_before>#include <catch.hpp>
#include <rapidcheck-catch.h>

#include "detail/MapParser.h"

using namespace rc;
using namespace rc::detail;

TEST_CASE("parseMap") {
    SECTION("parses empty string (or only whitespace) as empty map") {
        REQUIRE(parseMap("").empty());
        REQUIRE(parseMap("\n\t   ").empty());
    }

    SECTION("parses basic maps") {
        auto map = parseMap("foo=bar baz=1337");
        std::map<std::string, std::string> expected = {
            {"foo", "bar"},
            {"baz", "1337"}
        };

        REQUIRE(map == expected);
    }

    SECTION("ignores whitespace") {
        auto map = parseMap(" \n  foo =   bar \t  baz =  1337 ");
        std::map<std::string, std::string> expected = {
            {"foo", "bar"},
            {"baz", "1337"}
        };

        REQUIRE(map == expected);
    }

    SECTION("parses keys not followed by '=' as missing value") {
        auto map = parseMap("foo=bar baz");
        REQUIRE(map["baz"] == "");
    }

    SECTION("parses empty values") {
        auto map = parseMap("foo=bar baz=");
        REQUIRE(map["baz"] == "");
    }

    SECTION("parses double quoted string values") {
        auto map = parseMap(
            "foo=bar baz=\"testing 1 2 3 \"  stuff=cool");
        REQUIRE(map["baz"] == "testing 1 2 3 ");
    }

    SECTION("parses single quoted string values") {
        auto map = parseMap(
            "foo=bar baz='testing 1 2 3 ' stuff=cool");
        REQUIRE(map["baz"] == "testing 1 2 3 ");
    }

    SECTION("allows escaping of quotes in double quoted strings") {
        auto map = parseMap(
            "foo=bar baz=\"quote \\\"some\\\" stuff\" stuff=cool");
        REQUIRE(map["baz"] == "quote \"some\" stuff");
    }

    SECTION("allows escaping of quotes in single quoted strings") {
        auto map = parseMap(
            "foo=bar baz='quote \\'some\\' stuff' stuff=cool");
        REQUIRE(map["baz"] == "quote 'some' stuff");
    }

    SECTION("allows escaping of backslash in double quoted strings") {
        auto map = parseMap(
            "foo=bar baz=\"this\\\\that\" stuff=cool");
        REQUIRE(map["baz"] == "this\\that");
    }

    SECTION("allows escaping of backslash in single quoted strings") {
        auto map = parseMap(
            "foo=bar baz='this\\\\that' stuff=cool");
        REQUIRE(map["baz"] == "this\\that");
    }

    SECTION("allows escaping of normal characters in double quoted string") {
        auto map = parseMap(
            "foo=bar baz=\"\\f\\o\\o\\b\\a\\r\" stuff=cool");
        REQUIRE(map["baz"] == "foobar");
    }

    SECTION("allows escaping of normal characters in single quoted string") {
        auto map = parseMap(
            "foo=bar baz='\\f\\o\\o\\b\\a\\r' stuff=cool");
        REQUIRE(map["baz"] == "foobar");
    }

    SECTION("allows double quoted keys") {
        auto map = parseMap(" \"\\\"this=\\\\=that\\\"\"=foobar");
        REQUIRE(map["\"this=\\=that\""] == "foobar");
    }

    SECTION("allows single quoted keys") {
        auto map = parseMap(" '\\'this=\\\\=that\\''=foobar");
        REQUIRE(map["'this=\\=that'"] == "foobar");
    }

    SECTION("if there are duplicate keys, the last value takes precedence") {
        auto map = parseMap("foo=this foo=that");
        REQUIRE(map["foo"] == "that");
    }

    SECTION("throws ParseException on unterminated double quoted string") {
        REQUIRE_THROWS_AS(parseMap("foo=\"bar"), ParseException);
    }

    SECTION("throws ParseException on unterminated single quoted string") {
        REQUIRE_THROWS_AS(parseMap("foo='bar"), ParseException);
    }
}

TEST_CASE("mapToString") {
    prop("parseMap(mapToString(x)) == x",
         [] (const std::map<std::string, std::string> &map) {
             RC_PRE(map.find("") == map.end());
             RC_ASSERT(parseMap(mapToString(map)) == map);
         });
<commit_msg>Move MapParserTests to new framework<commit_after>#include <catch.hpp>
#include <rapidcheck-catch.h>

#include "detail/MapParser.h"

using namespace rc;
using namespace rc::detail;

TEST_CASE("parseMap") {
    SECTION("parses empty string (or only whitespace) as empty map") {
        REQUIRE(parseMap("").empty());
        REQUIRE(parseMap("\n\t   ").empty());
    }

    SECTION("parses basic maps") {
        auto map = parseMap("foo=bar baz=1337");
        std::map<std::string, std::string> expected = {
            {"foo", "bar"},
            {"baz", "1337"}
        };

        REQUIRE(map == expected);
    }

    SECTION("ignores whitespace") {
        auto map = parseMap(" \n  foo =   bar \t  baz =  1337 ");
        std::map<std::string, std::string> expected = {
            {"foo", "bar"},
            {"baz", "1337"}
        };

        REQUIRE(map == expected);
    }

    SECTION("parses keys not followed by '=' as missing value") {
        auto map = parseMap("foo=bar baz");
        REQUIRE(map["baz"] == "");
    }

    SECTION("parses empty values") {
        auto map = parseMap("foo=bar baz=");
        REQUIRE(map["baz"] == "");
    }

    SECTION("parses double quoted string values") {
        auto map = parseMap(
            "foo=bar baz=\"testing 1 2 3 \"  stuff=cool");
        REQUIRE(map["baz"] == "testing 1 2 3 ");
    }

    SECTION("parses single quoted string values") {
        auto map = parseMap(
            "foo=bar baz='testing 1 2 3 ' stuff=cool");
        REQUIRE(map["baz"] == "testing 1 2 3 ");
    }

    SECTION("allows escaping of quotes in double quoted strings") {
        auto map = parseMap(
            "foo=bar baz=\"quote \\\"some\\\" stuff\" stuff=cool");
        REQUIRE(map["baz"] == "quote \"some\" stuff");
    }

    SECTION("allows escaping of quotes in single quoted strings") {
        auto map = parseMap(
            "foo=bar baz='quote \\'some\\' stuff' stuff=cool");
        REQUIRE(map["baz"] == "quote 'some' stuff");
    }

    SECTION("allows escaping of backslash in double quoted strings") {
        auto map = parseMap(
            "foo=bar baz=\"this\\\\that\" stuff=cool");
        REQUIRE(map["baz"] == "this\\that");
    }

    SECTION("allows escaping of backslash in single quoted strings") {
        auto map = parseMap(
            "foo=bar baz='this\\\\that' stuff=cool");
        REQUIRE(map["baz"] == "this\\that");
    }

    SECTION("allows escaping of normal characters in double quoted string") {
        auto map = parseMap(
            "foo=bar baz=\"\\f\\o\\o\\b\\a\\r\" stuff=cool");
        REQUIRE(map["baz"] == "foobar");
    }

    SECTION("allows escaping of normal characters in single quoted string") {
        auto map = parseMap(
            "foo=bar baz='\\f\\o\\o\\b\\a\\r' stuff=cool");
        REQUIRE(map["baz"] == "foobar");
    }

    SECTION("allows double quoted keys") {
        auto map = parseMap(" \"\\\"this=\\\\=that\\\"\"=foobar");
        REQUIRE(map["\"this=\\=that\""] == "foobar");
    }

    SECTION("allows single quoted keys") {
        auto map = parseMap(" '\\'this=\\\\=that\\''=foobar");
        REQUIRE(map["'this=\\=that'"] == "foobar");
    }

    SECTION("if there are duplicate keys, the last value takes precedence") {
        auto map = parseMap("foo=this foo=that");
        REQUIRE(map["foo"] == "that");
    }

    SECTION("throws ParseException on unterminated double quoted string") {
        REQUIRE_THROWS_AS(parseMap("foo=\"bar"), ParseException);
    }

    SECTION("throws ParseException on unterminated single quoted string") {
        REQUIRE_THROWS_AS(parseMap("foo='bar"), ParseException);
    }
}

TEST_CASE("mapToString") {
    newprop(
        "parseMap(mapToString(x)) == x",
        [](const std::map<std::string, std::string> &map) {
            RC_PRE(map.find("") == map.end());
            RC_ASSERT(parseMap(mapToString(map)) == map);
        });

{'fraction_non_alphanumeric': 0.17992813141683778, 'fraction_numerical': 0.007186858316221766, 'mean_word_length': 2.377980060684872, 'pattern_counts': {'":': 0, '<': 13, '<?xml version=': 0, '>': 13, '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': '7224637', 'n_tokens_mistral': 2629, 'n_tokens_neox': 2420, 'n_words': 587}