55#include < IO/Operators.h>
66#include < Common/NamedCollections/NamedCollectionConfiguration.h>
77#include < Poco/Util/AbstractConfiguration.h>
8+ #include < Common/FieldVisitorToString.h>
89
910#include < fmt/ranges.h>
1011
@@ -16,6 +17,7 @@ namespace ErrorCodes
1617{
1718 extern const int NAMED_COLLECTION_IS_IMMUTABLE;
1819 extern const int BAD_ARGUMENTS;
20+ extern const int NOT_IMPLEMENTED;
1921}
2022
2123namespace Configuration = NamedCollectionConfiguration;
@@ -176,27 +178,14 @@ class NamedCollection::Impl
176178NamedCollection::NamedCollection (
177179 ImplPtr pimpl_,
178180 const std::string & collection_name_,
179- SourceId source_id_,
180- bool is_mutable_)
181+ const bool is_mutable_)
181182 : pimpl(std::move(pimpl_))
182183 , collection_name(collection_name_)
183- , source_id(source_id_)
184184 , is_mutable(is_mutable_)
185185{
186186}
187187
188- MutableNamedCollectionPtr NamedCollection::create (
189- const Poco::Util::AbstractConfiguration & config,
190- const std::string & collection_name,
191- const std::string & collection_path,
192- const Keys & keys,
193- SourceId source_id,
194- bool is_mutable)
195- {
196- auto impl = Impl::create (config, collection_name, collection_path, keys);
197- return std::unique_ptr<NamedCollection>(
198- new NamedCollection (std::move (impl), collection_name, source_id, is_mutable));
199- }
188+ NamedCollection::~NamedCollection () = default ;
200189
201190bool NamedCollection::has (const Key & key) const
202191{
@@ -297,8 +286,7 @@ MutableNamedCollectionPtr NamedCollection::duplicate() const
297286 std::lock_guard lock (mutex);
298287 auto impl = pimpl->createCopy (collection_name);
299288 return std::unique_ptr<NamedCollection>(
300- new NamedCollection (
301- std::move (impl), collection_name, SourceId::NONE, true ));
289+ new NamedCollection (std::move (impl), collection_name, true ));
302290}
303291
304292NamedCollection::Keys NamedCollection::getKeys (ssize_t depth, const std::string & prefix) const
@@ -334,6 +322,136 @@ std::unique_lock<std::mutex> NamedCollection::lock()
334322 return std::unique_lock (mutex);
335323}
336324
325+
326+ void NamedCollection::update (const ASTAlterNamedCollectionQuery & /* query*/ )
327+ {
328+ throw Exception (
329+ ErrorCodes::NOT_IMPLEMENTED,
330+ " update() not implemented for NamedCollection base class." );
331+ }
332+
333+ NamedCollectionFromConfig::NamedCollectionFromConfig (
334+ const Poco::Util::AbstractConfiguration & config_,
335+ const std::string & collection_name_,
336+ const std::string & collection_path_,
337+ const Keys & keys_)
338+ : NamedCollection(Impl::create(config_, collection_name_, collection_path_, keys_), collection_name_, /* is_mutable */ false )
339+ {
340+ }
341+
342+ MutableNamedCollectionPtr NamedCollectionFromConfig::create (
343+ const Poco::Util::AbstractConfiguration & config_,
344+ const std::string & collection_name_,
345+ const std::string & collection_path_,
346+ const Keys & keys_)
347+ {
348+ return std::unique_ptr<NamedCollection>(
349+ new NamedCollectionFromConfig (config_, collection_name_, collection_path_, keys_));
350+ }
351+
352+
353+ MutableNamedCollectionPtr NamedCollectionFromSQL::create (const ASTCreateNamedCollectionQuery & query)
354+ {
355+ return std::unique_ptr<NamedCollection>(new NamedCollectionFromSQL (query));
356+ }
357+
358+ NamedCollectionFromSQL::NamedCollectionFromSQL (const ASTCreateNamedCollectionQuery & query_)
359+ : NamedCollection(nullptr , query_.collection_name, true )
360+ , create_query_ptr(query_.clone()->as<ASTCreateNamedCollectionQuery &>())
361+ {
362+ const auto config = NamedCollectionConfiguration::createConfiguration (collection_name, create_query_ptr.changes , create_query_ptr.overridability );
363+
364+ std::set<std::string, std::less<>> keys;
365+ for (const auto & [name, _] : create_query_ptr.changes )
366+ keys.insert (name);
367+
368+ pimpl = Impl::create (*config, collection_name, " " , keys);
369+ }
370+
371+ String NamedCollectionFromSQL::getCreateStatement (bool show_secrects)
372+ {
373+ auto & changes = create_query_ptr.changes ;
374+ std::sort (
375+ changes.begin (), changes.end (),
376+ [](const SettingChange & lhs, const SettingChange & rhs) { return lhs.name < rhs.name ; });
377+
378+ return create_query_ptr.formatWithPossiblyHidingSensitiveData (
379+ /* max_length=*/ 0 ,
380+ /* one_line=*/ true ,
381+ /* show_secrets=*/ show_secrects,
382+ /* print_pretty_type_names=*/ false ,
383+ /* identifier_quoting_rule=*/ IdentifierQuotingRule::WhenNecessary,
384+ /* identifier_quoting_style=*/ IdentifierQuotingStyle::Backticks);
385+ }
386+
387+ void NamedCollectionFromSQL::update (const ASTAlterNamedCollectionQuery & alter_query)
388+ {
389+ std::lock_guard lock (mutex);
390+
391+ std::unordered_map<std::string, Field> result_changes_map;
392+ for (const auto & [name, value] : alter_query.changes )
393+ {
394+ auto [it, inserted] = result_changes_map.emplace (name, value);
395+ if (!inserted)
396+ {
397+ throw Exception (
398+ ErrorCodes::BAD_ARGUMENTS,
399+ " Value with key `{}` is used twice in the SET query (collection name: {})" ,
400+ name, alter_query.collection_name );
401+ }
402+ }
403+
404+ for (const auto & [name, value] : create_query_ptr.changes )
405+ result_changes_map.emplace (name, value);
406+
407+ std::unordered_map<std::string, bool > result_overridability_map;
408+ for (const auto & [name, value] : alter_query.overridability )
409+ result_overridability_map.emplace (name, value);
410+ for (const auto & [name, value] : create_query_ptr.overridability )
411+ result_overridability_map.emplace (name, value);
412+
413+ for (const auto & delete_key : alter_query.delete_keys )
414+ {
415+ auto it = result_changes_map.find (delete_key);
416+ if (it == result_changes_map.end ())
417+ {
418+ throw Exception (
419+ ErrorCodes::BAD_ARGUMENTS,
420+ " Cannot delete key `{}` because it does not exist in collection" ,
421+ delete_key);
422+ }
423+
424+ result_changes_map.erase (it);
425+ auto it_override = result_overridability_map.find (delete_key);
426+ if (it_override != result_overridability_map.end ())
427+ result_overridability_map.erase (it_override);
428+ }
429+
430+ create_query_ptr.changes .clear ();
431+ for (const auto & [name, value] : result_changes_map)
432+ create_query_ptr.changes .emplace_back (name, value);
433+ create_query_ptr.overridability = std::move (result_overridability_map);
434+
435+ if (create_query_ptr.changes .empty ())
436+ throw Exception (
437+ ErrorCodes::BAD_ARGUMENTS,
438+ " Named collection cannot be empty (collection name: {})" ,
439+ collection_name);
440+
441+ chassert (create_query_ptr.collection_name == alter_query.collection_name );
442+ for (const auto & [name, value] : alter_query.changes )
443+ {
444+ auto it_override = alter_query.overridability .find (name);
445+ if (it_override != alter_query.overridability .end ())
446+ setOrUpdate<String, true >(name, convertFieldToString (value), it_override->second );
447+ else
448+ setOrUpdate<String, true >(name, convertFieldToString (value), {});
449+ }
450+
451+ for (const auto & key : alter_query.delete_keys )
452+ remove<true >(key);
453+ }
454+
337455template String NamedCollection::get<String>(const NamedCollection::Key & key) const ;
338456template UInt64 NamedCollection::get<UInt64>(const NamedCollection::Key & key) const ;
339457template Int64 NamedCollection::get<Int64>(const NamedCollection::Key & key) const ;
0 commit comments