@@ -327,31 +327,68 @@ Strings BuildSystemConfigInsertions::getStrings()
327327
328328void Patch::load (const yaml &root)
329329{
330- get_map_and_iterate (root, " replace_in_files " , [ this ](auto &v )
330+ auto load_replace = [&root ](auto &a, const String &k )
331331 {
332- if (!v.second .IsMap ())
333- throw std::runtime_error (" Members of 'replace_in_files' should be maps" );
334- if (!(v.second [" from" ].IsDefined () && v.second [" to" ].IsDefined ()))
335- throw std::runtime_error (" There are no 'from' and 'to' inside 'replace_in_files'" );
336- auto from = v.second [" from" ].template as <String>();
337- auto to = v.second [" to" ].template as <String>();
338- replace_in_files[from] = to;
339- });
332+ get_map_and_iterate (root, k, [&a, &k](auto &v)
333+ {
334+ auto k = v.first .template as <String>();
335+ if (v.second .IsScalar ())
336+ {
337+ auto vv = v.second .template as <String>();
338+ a.emplace_back (k, vv);
339+ }
340+ else if (v.second .IsMap ())
341+ {
342+ if (!(v.second [" from" ].IsDefined () && v.second [" to" ].IsDefined ()))
343+ throw std::runtime_error (" There are no 'from' and 'to' inside '" + k + " '" );
344+ auto from = v.second [" from" ].template as <String>();
345+ auto to = v.second [" to" ].template as <String>();
346+ a.emplace_back (from, to);
347+ }
348+ else
349+ throw std::runtime_error (" Members of '" + k + " ' must be scalars or maps" );
350+ });
351+ };
352+ load_replace (replace, " replace" );
353+ load_replace (regex_replace, " regex_replace" );
340354}
341355
342356void Patch::save (yaml &node) const
343357{
344- yaml root;
345- for (auto &r : replace_in_files)
346- root[r.first ] = r.second ;
347- if (!replace_in_files.empty ())
348- node[" patch" ] = root;
358+ auto save_replace = [&node](const auto &a, const auto &k)
359+ {
360+ if (a.empty ())
361+ return ;
362+ yaml root;
363+ for (auto &r : a)
364+ root[r.first ] = r.second ;
365+ node[" patch" ][k] = root;
366+ };
367+ save_replace (replace, " replace" );
368+ save_replace (regex_replace, " regex_replace" );
369+ }
370+
371+ void Patch::patchSources (const Files &files) const
372+ {
373+ if (replace.empty () && regex_replace.empty ())
374+ return ;
375+ std::vector<std::pair<std::regex, String>> regex_prepared;
376+ for (auto &p : regex_replace)
377+ regex_prepared.emplace_back (std::regex (p.first ), p.second );
378+ for (auto &f : files)
379+ {
380+ auto s = read_file (f, true );
381+ for (auto &p : replace)
382+ boost::algorithm::replace_all (s, p.first , p.second );
383+ for (auto &p : regex_prepared)
384+ s = std::regex_replace (s, p.first , p.second );
385+ write_file_if_different (f, s);
386+ }
349387}
350388
351389Project::Project ()
352390 : Project(ProjectPath())
353391{
354-
355392}
356393
357394Project::Project (const ProjectPath &root_project)
@@ -930,7 +967,7 @@ void Project::load(const yaml &root)
930967 aliases = get_sequence_set<String>(root, " aliases" );
931968 checks.load (root);
932969
933- auto patch_node = root[" patch" ];
970+ const auto & patch_node = root[" patch" ];
934971 if (patch_node.IsDefined ())
935972 patch.load (patch_node);
936973
@@ -1176,17 +1213,7 @@ void Project::prepareExports() const
11761213
11771214void Project::patchSources () const
11781215{
1179- if (!patch.replace_in_files .empty ())
1180- {
1181- auto &srcs = getSources ();
1182- for (auto &f : srcs)
1183- {
1184- auto s = read_file (f, true );
1185- for (auto &p : patch.replace_in_files )
1186- boost::algorithm::replace_all (s, p.first , p.second );
1187- write_file_if_different (f, s);
1188- }
1189- }
1216+ patch.patchSources (getSources ());
11901217}
11911218
11921219const Files &Project::getSources () const
0 commit comments