/* * This file is a part of morm * and is distributed under the 2-Clause BSD licence. * Author: Tomasz Sowa */ /* * Copyright (c) 2018-2023, Tomasz Sowa * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * 1. Redistributions of source code must retain the above copyright notice, * this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. * */ #ifndef headerfile_morm_src_baseexpression #define headerfile_morm_src_baseexpression #include #include #include #include "textstream/textstream.h" #include "date/date.h" #include "morm_types.h" #include "modelenv.h" #include "ft.h" #include "export.h" #include "convert/text.h" #ifdef MORM_HAS_EZC_LIBRARY #include "funinfo.h" #endif namespace morm { class Model; class ModelConnector; class BaseExpression { public: BaseExpression(); virtual ~BaseExpression(); BaseExpression(const BaseExpression &) = delete; BaseExpression(BaseExpression &&) = delete; virtual void set_work_mode(int work_mode); virtual int get_work_mode(); virtual void set_output_type(int output_type); virtual int get_output_type(); virtual pt::TextStream * get_text_stream(); virtual void set_text_stream(pt::TextStream * out_stream); virtual void clear(); virtual void generate_from_model(pt::TextStream & stream, Model & model); virtual void generate_from_model(pt::TextStream & stream, Model & model, const FT & field_type); virtual pt::TextStream * get_current_stream(); // rename me virtual void allow_to_use_prefix(bool use_prefix); virtual bool get_allow_to_use_prefix(); template void field(const wchar_t * field_name, const FieldValue & field_value, const FT & field_type, ModelEnv * model_env) { field_generic(field_name, field_value, nullptr, field_type, model_env); } virtual void field(const wchar_t * field_name, void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env) { int tmp_object = 0; field_generic(field_name, tmp_object, getter_method, field_type, model_env); } template void field_generic(const wchar_t * field_name, const FieldValue & field_value, void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env) { if( out_stream && can_field_be_generated(field_type) ) { field_before(); if( work_mode == MORM_WORK_MODE_MODEL_FIELDS ) { put_field_name_and_table_if_needed(field_name, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_SAVE_FIELDS ) { save_foreign_key(field_name, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_VALUES ) { put_field_value_or_null(field_value, getter_method, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES ) { put_field_name_and_value(field_name, field_value, getter_method, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES_FIELDS ) { put_field_name_and_value_and_closing_name(field_name, field_value, getter_method, field_type, model_env); } field_after(); } } template void field_in(pt::TextStream & stream, const wchar_t * field_name, const std::set & container, ModelEnv * model_env) { field_in_generic>(stream, field_name, container, model_env); } template void field_in(pt::TextStream & stream, const wchar_t * field_name, const std::list & container, ModelEnv * model_env) { field_in_generic>(stream, field_name, container, model_env); } template void field_in(pt::TextStream & stream, const wchar_t * field_name, const std::vector & container, ModelEnv * model_env) { field_in_generic>(stream, field_name, container, model_env); } template void field_list(const wchar_t * field_name, ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env, IsContainerByValueRenameMe * foo) { if( out_stream && can_field_be_generated(field_type) && can_field_list_be_generated(field_type) ) { field_before(); // if( work_mode == MORM_WORK_MODE_MODEL_FIELDS ) // { // put_field_name_and_table_if_needed(field_name); // } // else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES ) { put_field_name_and_value_list(field_name, field_value, model_container_type, field_type, model_connector, model_env, foo); } else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES_FIELDS ) { put_field_name_and_value_list_and_closing_name(field_name, field_value, model_container_type, field_type, model_connector, model_env, foo); } field_after(); } } template void field_model(const wchar_t * field_name, ModelClass & field_model, const FT & field_type, ModelEnv * model_env) { if( out_stream && can_field_be_generated(field_type) && can_field_model_be_generated(field_model.get_has_primary_key_set(), field_type) ) { field_before(); if( work_mode == MORM_WORK_MODE_MODEL_FIELDS ) { if( output_type == MORM_OUTPUT_TYPE_FIELDS_RECURSIVE ) generate_from_model(field_model, field_type); else put_field_name_and_table_if_needed(field_name, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_VALUES ) { generate_from_model(field_model, field_type); } else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES ) { put_field_name_and_value_model(field_name, field_model, field_type, model_env); } else if( work_mode == MORM_WORK_MODE_MODEL_FIELDS_VALUES_FIELDS ) { put_field_name_and_value_model_and_closing_name(field_name, field_model, field_type, model_env); } field_after(); } } template void field_to_stream(pt::TextStream & stream, const wchar_t * field_name, const FieldValue & field_value, const FT & field_type, ModelEnv * model_env) { this->out_stream = &stream; field(field_name, field_value, field_type, model_env); this->out_stream = nullptr; } template void value_to_stream(pt::TextStream & stream, const FieldValue & field_value, const FT & field_type, ModelEnv * model_env = nullptr) { this->out_stream = &stream; put_field_value(field_value, field_type, model_env); this->out_stream = nullptr; } virtual void put_schema_table(const wchar_t * schema_name, const wchar_t * table_name); virtual void put_schema_table(const pt::WTextStream & schema_name, const pt::WTextStream & table_name); virtual void put_table(const wchar_t * table_name); virtual void put_table(const pt::WTextStream & table_name); virtual void put_table_with_index(const wchar_t * table_name, int index); virtual void put_table_with_index(const pt::WTextStream & table_name, int index); virtual void put_table_with_index_and_field(const wchar_t * table_name, int index, const wchar_t * field_name, const FT & field_type); virtual void put_table_with_index_and_field(const pt::WTextStream & table_name, int index, const wchar_t * field_name, const FT & field_type); virtual void put_table_and_field(const wchar_t * table_name, const wchar_t * field_name, const FT & field_type); virtual void put_table_and_field(const pt::WTextStream & table_name, const wchar_t * field_name, const FT & field_type); virtual void put_alias(const pt::WTextStream & alias_name, int index); virtual void put_alias(const pt::WTextStream & alias_name_prefix, int index, const wchar_t * alias_name_postfix); virtual void put_string(const char * str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void put_string(const wchar_t * str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void put_string(const std::string & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void put_string(const std::wstring & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void put_stream(const pt::TextStream & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void put_stream(const pt::WTextStream & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void schema_table_to_stream(pt::TextStream & stream, const wchar_t * schema_name, const wchar_t * table_name); virtual void schema_table_to_stream(pt::TextStream & stream, const pt::WTextStream & schema_name, const pt::WTextStream & table_name); virtual void table_to_stream(pt::TextStream & stream, const wchar_t * table_name); virtual void table_to_stream(pt::TextStream & stream, const pt::WTextStream & table_name); virtual void table_with_index_to_stream(pt::TextStream & stream, const wchar_t * table_name, int index); virtual void table_with_index_to_stream(pt::TextStream & stream, const pt::WTextStream & table_name, int index); virtual void table_with_index_and_field_to_stream(pt::TextStream & stream, const wchar_t * table_name, int index, const wchar_t * field_name, const FT & field_type); virtual void table_with_index_and_field_to_stream(pt::TextStream & stream, const pt::WTextStream & table_name, int index, const wchar_t * field_name, const FT & field_type); virtual void table_and_field_to_stream(pt::TextStream & stream, const wchar_t * table_name, const wchar_t * field_name, const FT & field_type); virtual void table_and_field_to_stream(pt::TextStream & stream, const pt::WTextStream & table_name, const wchar_t * field_name, const FT & field_type); virtual void alias_to_stream(pt::TextStream & stream, const pt::WTextStream & alias_name, int index); virtual void alias_to_stream(pt::TextStream & stream, const pt::WTextStream & alias_name_prefix, int index, const wchar_t * alias_name_postfix); virtual void string_to_stream(pt::TextStream & stream, const char * str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void string_to_stream(pt::TextStream & stream, const wchar_t * str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void string_to_stream(pt::TextStream & stream, const std::string & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void string_to_stream(pt::TextStream & stream, const std::wstring & str, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void stream_to_stream(pt::TextStream & stream_out, const pt::TextStream & stream_in, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); virtual void stream_to_stream(pt::TextStream & stream_out, const pt::WTextStream & stream_in, const FT & field_type, bool add_quotes = false, ModelEnv * model_env = nullptr); template void put_string_generic(const StringType * str, const FT & field_type, bool add_quotes, ModelEnv * model_env = nullptr) { if( out_stream ) { if( add_quotes ) { before_field_value_string(field_type, model_env); } esc(str, *out_stream, field_type, model_env); if( add_quotes ) { after_field_value_string(field_type, model_env); } } } template void put_string_generic(const StringOrStreamType & str, const FT & field_type, bool add_quotes, ModelEnv * model_env = nullptr) { if( out_stream ) { if( add_quotes ) { before_field_value_string(field_type, model_env); } esc(str, *out_stream, field_type, model_env); if( add_quotes ) { after_field_value_string(field_type, model_env); } } } /* * IMPLEMENT ME * esc for: signed char, wchar_t, char16_t, char32_t * */ virtual bool esc_char(char val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual bool esc_char(wchar_t val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(char val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(unsigned char val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(wchar_t val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const std::wstring & val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const wchar_t * val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const std::string & val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const char * val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(bool val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(short val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(unsigned short val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(int val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(unsigned int val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(long val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(unsigned long val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(long long val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(unsigned long long val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(float val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(double val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(long double val, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const pt::Date & date, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const pt::TextStream & val,pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const pt::WTextStream & val,pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); virtual void esc(const pt::Space & space, pt::TextStream & stream, const FT & field_type = FT::default_type, ModelEnv * model_env = nullptr); protected: int work_mode; /* what to do: generating fields list, values list or fields-values list */ int output_type; bool is_first_field; pt::TextStream * out_stream; bool use_prefix; pt::TextStream scratch_buffer_local; pt::TextStream * scratch_buffer; virtual void generate_from_model(Model & model, const FT & field_type); virtual void before_generate_from_model(); virtual void after_generate_from_model(); virtual bool can_field_be_generated(const FT &); virtual bool can_field_model_be_generated(bool has_model_primary_key, const FT & field_type); virtual bool can_field_list_be_generated(const FT &); virtual bool should_field_model_be_generated_as_null(bool has_model_primary_key, const FT & field_type); virtual void field_before(); virtual void field_after(); virtual void put_field_name_and_table_if_needed(const wchar_t * field_name, const FT & field_type, ModelEnv * model_env); virtual void put_field_name(const wchar_t * field_name, const FT & field_type, ModelEnv * model_env); virtual void put_field_closing_name(const wchar_t * field_name, const FT & field_type, ModelEnv * model_env); virtual void put_value_list_opening_index(size_t index, const FT & field_type); virtual void put_value_list_closing_index(size_t index, const FT & field_type); virtual void save_foreign_key(const wchar_t * field_name, const FT & field_type, ModelEnv * model_env); virtual void dump_additional_info(Model & model); virtual void add_additional_columns(Model & model); template void put_field_value(const FieldValue & field_value, const FT & field_type, ModelEnv * model_env = nullptr) { if( out_stream ) { before_field_value(field_value, field_type, model_env); esc(field_value, *out_stream, field_type, model_env); after_field_value(field_value, field_type, model_env); } } void put_field_value(void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env = nullptr) { if( out_stream && model_env && model_env->model && getter_method ) { before_field_value_string(field_type, model_env); if( scratch_buffer ) { scratch_buffer->clear(); (model_env->model->*getter_method)(*scratch_buffer); esc(*scratch_buffer, *out_stream, field_type, model_env); scratch_buffer->clear(); } after_field_value_string(field_type, model_env); } } virtual void put_null_value() { (*out_stream) << "null"; } virtual void before_field_value_list() { } virtual void after_field_value_list() { } virtual void field_value_list_separator() { (*out_stream) << ","; } virtual void put_statement_in_starts() { (*out_stream) << "("; } virtual void put_statement_in_ends() { (*out_stream) << ") "; } template void put_field_value_list(ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env, IsContainerByValueRenameMe * foo) { if constexpr (std::is_base_of()) { if constexpr (std::is_base_of()) { put_field_value_list_model_by_value(field_value, model_container_type, field_type, model_connector, model_env); } else { put_field_value_list_model_by_pointer(field_value, model_container_type, field_type, model_connector, model_env); } } else { put_field_value_list_non_model(field_value, model_connector, field_type); } } template void put_field_value_list_model_by_value(ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env) { if( model_connector && model_env && out_stream ) { before_field_value_list(); size_t index = 0; for(auto & child_model_item : field_value) { if( can_field_model_be_generated(child_model_item.get_has_primary_key_set(), field_type) ) { if( index > 0 ) { field_value_list_separator(); } put_value_list_opening_index(index, field_type); put_field_value_list_model(child_model_item, model_connector, model_env); put_value_list_closing_index(index, field_type); index += 1; } } after_field_value_list(); } } template void put_field_value_list_model_by_pointer(ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env) { if( model_connector && model_env && out_stream ) { before_field_value_list(); size_t index = 0; for(auto * child_model_item : field_value) { if( can_field_model_be_generated(child_model_item->get_has_primary_key_set(), field_type) ) { if( index > 0 ) { field_value_list_separator(); } put_value_list_opening_index(index, field_type); put_field_value_list_model(*child_model_item, model_connector, model_env); put_value_list_closing_index(index, field_type); index += 1; } } after_field_value_list(); } } template void put_field_value_list_model(ModelContainerType & child_model, ModelConnector * model_connector, ModelEnv * model_env) { ModelEnv model_env_local(*model_env); child_model.model_env = &model_env_local; child_model.model_env->has_primary_key_set = child_model.get_has_primary_key_set(); child_model.model_env->model = &child_model; child_model.set_connector(model_connector); FT field_type = FT::default_type; generate_from_model(child_model, field_type); child_model.model_env = nullptr; } template void put_field_value_list_non_model(ModelContainer & field_value, ModelConnector * model_connector, const FT & field_type) { if( model_connector && out_stream ) { before_field_value_list(); size_t index = 0; for(const auto & m : field_value) { if( index > 0 ) { field_value_list_separator(); } put_value_list_opening_index(index, field_type); put_field_value(m, FT::default_type); put_value_list_closing_index(index, field_type); index += 1; } after_field_value_list(); } } // used in 'in()' statements, may should be renamed? template void field_in_generic(pt::TextStream & stream, const wchar_t * field_name, const Container & container, ModelEnv * model_env) { // IMPROVE ME // what about if container is empty? // only 'in()' statement would be generated this->out_stream = &stream; field_before(); put_field_name_and_table_if_needed(field_name, FT::default_type, model_env); put_name_value_separator(); bool is_first = true; put_statement_in_starts(); for(const FieldValue & v : container) { if( !is_first ) { field_value_list_separator(); } put_field_value(v, FT::default_type, model_env); is_first = false; } put_statement_in_ends(); field_after(); this->out_stream = nullptr; } virtual void schema_table_separator(); virtual void table_field_separator(); virtual void alias_names_separator(); virtual void before_schema_name(); virtual void after_schema_name(); virtual void before_table_name(); virtual void after_table_name(); virtual void before_field_name(); virtual void after_field_name(); virtual void before_alias_name(); virtual void after_alias_name(); virtual void before_field_value(const std::wstring &, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const std::wstring &, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(const std::string &, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const std::string &, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(const wchar_t *, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const wchar_t *, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(const char *, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const char *, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(wchar_t, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(wchar_t, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(char, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(char, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(const pt::Date &, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const pt::Date &, const FT & field_type, ModelEnv * model_env); virtual void before_field_value(const pt::Space &, const FT & field_type, ModelEnv * model_env); virtual void after_field_value(const pt::Space &, const FT & field_type, ModelEnv * model_env); template void before_field_value(const FieldValue &, const FT & field_type, ModelEnv * model_env) { } template void after_field_value(const FieldValue &, const FT & field_type, ModelEnv * model_env) { } virtual void put_name_value_separator(); /* * IMPLEMENT ME * put_type for: signed char, wchar_t, char16_t, char32_t * */ // virtual void put_type(char val, pt::TextStream & stream); // virtual void put_type(unsigned char val, pt::TextStream & stream); // // virtual void put_type(const std::wstring & val, pt::TextStream & stream); // virtual void put_type(const wchar_t * val, pt::TextStream & stream); // // virtual void put_type(const std::string & val, pt::TextStream & stream); // virtual void put_type(const char * val, pt::TextStream & stream); // // virtual void put_type(bool val, pt::TextStream & stream); // virtual void put_type(short val, pt::TextStream & stream); // virtual void put_type(unsigned short val, pt::TextStream & stream); // virtual void put_type(int val, pt::TextStream & stream); // virtual void put_type(unsigned int val, pt::TextStream & stream); // virtual void put_type(long val, pt::TextStream & stream); // virtual void put_type(unsigned long val, pt::TextStream & stream); // virtual void put_type(long long val, pt::TextStream & stream); // virtual void put_type(unsigned long long val, pt::TextStream & stream); // virtual void put_type(float val, pt::TextStream & stream); // virtual void put_type(double val, pt::TextStream & stream); // virtual void put_type(long double val, pt::TextStream & stream); //virtual void put_type(void* val, pt::TextStream & stream); // virtual void put_type(const pt::Date & date, pt::TextStream & stream); // virtual void put_type(const Model & model, pt::TextStream & stream); // // template // void put_type(const std::list & model, pt::TextStream & stream) // { // stream << "table"; // may just use std::list? // } // // template // void put_type(const std::vector & model, pt::TextStream & stream) // { // stream << "table"; // may just just std::vector? // } virtual void before_field_value_string(const FT & field_type, ModelEnv * model_env); virtual void after_field_value_string(const FT & field_type, ModelEnv * model_env); char char_to_hex_part(char c); void char_to_hex(char c, pt::TextStream & stream); void char_to_hex(wchar_t c, pt::TextStream & stream); void esc(const wchar_t * val, bool has_known_length, size_t len, pt::TextStream & stream, const FT & field_type, ModelEnv * model_env); void esc(const char * val, bool has_known_length, size_t len, pt::TextStream & stream, const FT & field_type, ModelEnv * model_env); bool is_empty_field(const wchar_t * value); template void esc_normal_string(CharType * val, bool has_known_length, size_t len, pt::TextStream & stream, const FT & field_type, ModelEnv * model_env) { for(size_t i = 0 ; has_known_length ? (i < len) : val[i] != 0 ; ++i) { esc(val[i], stream, field_type, model_env); } } template void esc_numeric_string(CharType * val, bool has_known_length, size_t len, pt::TextStream & stream, const FT & field_type, ModelEnv * model_env) { bool was_comma = false; bool was_something_printed = false; bool was_digit_printed = false; for(size_t i = 0 ; has_known_length ? (i < len) : val[i] != 0 ; ++i) { typename std::remove_const::type c = val[i]; if( c == ',' ) c = '.'; if( (c=='.' && !was_comma) || (c>='0' && c<='9') || (c=='-' && !was_something_printed) ) { if( c=='.' ) { if( !was_digit_printed ) { esc(static_cast('0'), stream, field_type, model_env); was_digit_printed = true; } was_comma = true; } esc(c, stream, field_type, model_env); was_something_printed = true; if( c>='0' && c<='9' ) { was_digit_printed = true; } } } if( !was_digit_printed ) { esc(static_cast('0'), stream, field_type, model_env); } } template void put_field_value_or_null(const FieldValue & field_value, void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env) { if( getter_method ) { put_field_value(getter_method, field_type, model_env); } else { if( field_type.is_primary_key() ) { if( model_env && model_env->has_primary_key_set ) put_field_value(field_value, field_type, model_env); else put_null_value(); } else { put_field_value(field_value, field_type, model_env); } } } template void put_field_name_and_value(const wchar_t * field_name, const FieldValue & field_value, void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env) { bool allow_to_put_value = (get_output_type() != MORM_OUTPUT_TYPE_WHERE_IS_NULL && get_output_type() != MORM_OUTPUT_TYPE_WHERE_IS_NOT_NULL); if( model_env && model_env->set_field_name_helper ) { if( (size_t)model_env->field_index < model_env->set_field_name_helper->size() ) { put_field_name_and_table_if_needed((*model_env->set_field_name_helper)[model_env->field_index], field_type, model_env); put_name_value_separator(); if( allow_to_put_value ) put_field_value_or_null(field_value, getter_method, field_type, model_env); } model_env->field_index += 1; } else { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); if( allow_to_put_value ) put_field_value_or_null(field_value, getter_method, field_type, model_env); } } template void put_field_name_and_value_list(const wchar_t * field_name, ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env, IsContainerByValueRenameMe * foo) { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); put_field_value_list(field_value, model_container_type, field_type, model_connector, model_env, foo); } template void put_field_name_and_value_model(const wchar_t * field_name, ModelClass & field_model, const FT & field_type, ModelEnv * model_env) { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); generate_from_model(field_model, field_type); } template void put_field_name_and_value_and_closing_name(const wchar_t * field_name, const FieldValue & field_value, void (Model::*getter_method)(pt::Stream &), const FT & field_type, ModelEnv * model_env) { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); put_field_value_or_null(field_value, getter_method, field_type, model_env); put_name_value_separator(); put_field_closing_name(field_name, field_type, model_env); } template void put_field_name_and_value_list_and_closing_name(const wchar_t * field_name, ModelContainer & field_value, ModelContainerType * model_container_type, const FT & field_type, ModelConnector * model_connector, ModelEnv * model_env, IsContainerByValueRenameMe * foo) { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); put_field_value_list(field_value, model_container_type, field_type, model_connector, model_env, foo); put_name_value_separator(); put_field_closing_name(field_name, field_type, model_env); } template void put_field_name_and_value_model_and_closing_name(const wchar_t * field_name, ModelClass & field_model, const FT & field_type, ModelEnv * model_env) { put_field_name_and_table_if_needed(field_name, field_type, model_env); put_name_value_separator(); generate_from_model(field_model, field_type); put_name_value_separator(); put_field_closing_name(field_name, field_type, model_env); } }; } #endif