diff --git a/jus/AbstractFunction.cpp b/jus/AbstractFunction.cpp index 6df9c7e..2f5d9de 100644 --- a/jus/AbstractFunction.cpp +++ b/jus/AbstractFunction.cpp @@ -6,120 +6,146 @@ #include #include -template<> bool convertJsonTo(const ejson::Value& _value) { +template<> bool jus::convertJsonTo(const ejson::Value& _value) { return _value.toBoolean().get(); } -template<> float convertJsonTo(const ejson::Value& _value) { +template<> float jus::convertJsonTo(const ejson::Value& _value) { return _value.toNumber().get(); } -template<> double convertJsonTo(const ejson::Value& _value) { +template<> double jus::convertJsonTo(const ejson::Value& _value) { return _value.toNumber().get(); } -template<> int64_t convertJsonTo(const ejson::Value& _value) { +template<> int64_t jus::convertJsonTo(const ejson::Value& _value) { return int64_t(_value.toNumber().get()); } -template<> int32_t convertJsonTo(const ejson::Value& _value) { +template<> int32_t jus::convertJsonTo(const ejson::Value& _value) { //_value.display(); return int32_t(_value.toNumber().get()); } -template<> int16_t convertJsonTo(const ejson::Value& _value) { +template<> int16_t jus::convertJsonTo(const ejson::Value& _value) { return int16_t(_value.toNumber().get()); } -template<> int8_t convertJsonTo(const ejson::Value& _value) { +template<> int8_t jus::convertJsonTo(const ejson::Value& _value) { return int8_t(_value.toNumber().get()); } -template<> uint64_t convertJsonTo(const ejson::Value& _value) { +template<> uint64_t jus::convertJsonTo(const ejson::Value& _value) { return uint64_t(_value.toNumber().get()); } -template<> uint32_t convertJsonTo(const ejson::Value& _value) { +template<> uint32_t jus::convertJsonTo(const ejson::Value& _value) { return uint32_t(_value.toNumber().get()); } -template<> uint16_t convertJsonTo(const ejson::Value& _value) { +template<> uint16_t jus::convertJsonTo(const ejson::Value& _value) { return uint16_t(_value.toNumber().get()); } -template<> uint8_t convertJsonTo(const ejson::Value& _value) { +template<> uint8_t jus::convertJsonTo(const ejson::Value& _value) { return uint8_t(_value.toNumber().get()); } -template<> std::string convertJsonTo(const ejson::Value& _value) { +template<> std::string jus::convertJsonTo(const ejson::Value& _value) { //_value.display(); return _value.toString().get(); } -template<> ejson::Value convertToJson(const bool& _value) { +template<> ejson::Value jus::convertToJson(const bool& _value) { return ejson::Boolean(_value); } -template<> ejson::Value convertToJson(const float& _value) { +template<> ejson::Value jus::convertToJson(const float& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const double& _value) { +template<> ejson::Value jus::convertToJson(const double& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const int64_t& _value) { +template<> ejson::Value jus::convertToJson(const int64_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const int32_t& _value) { +template<> ejson::Value jus::convertToJson(const int32_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const int16_t& _value) { +template<> ejson::Value jus::convertToJson(const int16_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const int8_t& _value) { +template<> ejson::Value jus::convertToJson(const int8_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const uint64_t& _value) { +template<> ejson::Value jus::convertToJson(const uint64_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const uint32_t& _value) { +template<> ejson::Value jus::convertToJson(const uint32_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const uint16_t& _value) { +template<> ejson::Value jus::convertToJson(const uint16_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const uint8_t& _value) { +template<> ejson::Value jus::convertToJson(const uint8_t& _value) { return ejson::Number(_value); } -template<> ejson::Value convertToJson(const std::string& _value) { +template<> ejson::Value jus::convertToJson(const std::string& _value) { return ejson::String(_value); } -template<> bool convertStringTo(const std::string& _value) { +template<> bool jus::convertStringTo(const std::string& _value) { return etk::string_to_bool(_value); } -template<> float convertStringTo(const std::string& _value) { +template<> float jus::convertStringTo(const std::string& _value) { return etk::string_to_float(_value); } -template<> double convertStringTo(const std::string& _value) { +template<> double jus::convertStringTo(const std::string& _value) { return etk::string_to_double(_value); } -template<> int64_t convertStringTo(const std::string& _value) { +template<> int64_t jus::convertStringTo(const std::string& _value) { return etk::string_to_int64_t(_value); } -template<> int32_t convertStringTo(const std::string& _value) { +template<> int32_t jus::convertStringTo(const std::string& _value) { return etk::string_to_int32_t(_value); } -template<> int16_t convertStringTo(const std::string& _value) { +template<> int16_t jus::convertStringTo(const std::string& _value) { return etk::string_to_int16_t(_value); } -template<> int8_t convertStringTo(const std::string& _value) { +template<> int8_t jus::convertStringTo(const std::string& _value) { return etk::string_to_int8_t(_value); } -template<> uint64_t convertStringTo(const std::string& _value) { +template<> uint64_t jus::convertStringTo(const std::string& _value) { return etk::string_to_uint64_t(_value); } -template<> uint32_t convertStringTo(const std::string& _value) { +template<> uint32_t jus::convertStringTo(const std::string& _value) { return etk::string_to_uint32_t(_value); } -template<> uint16_t convertStringTo(const std::string& _value) { +template<> uint16_t jus::convertStringTo(const std::string& _value) { return etk::string_to_uint16_t(_value); } -template<> uint8_t convertStringTo(const std::string& _value) { +template<> uint8_t jus::convertStringTo(const std::string& _value) { return etk::string_to_uint8_t(_value); } -template<> std::string convertStringTo(const std::string& _value) { +template<> std::string jus::convertStringTo(const std::string& _value) { return _value; } -bool AbstractFunction::checkCompatibility(const ParamType& _type, const ejson::Value& _params) { +const std::string& jus::AbstractFunction::getName() const { + return m_name; +} + +const std::string& jus::AbstractFunction::getDescription() const { + return m_description; +} + +void jus::AbstractFunction::setDescription(const std::string& _desc) { + m_description = _desc; +} + +void jus::AbstractFunction::setParam(int32_t _idParam, const std::string& _name, const std::string& _desc) { + JUS_TODO("not implemented set param ... '" << _name << "'"); +} + +void jus::AbstractFunction::addParam(const std::string& _name, const std::string& _desc) { + m_paramsDescription.push_back(std::make_pair(_name, _desc)); +} + +jus::AbstractFunction::AbstractFunction(const std::string& _name, + const std::string& _desc): + m_name(_name), + m_description(_desc) { + +} +bool jus::AbstractFunction::checkCompatibility(const ParamType& _type, const ejson::Value& _params) { if (createType() == _type) { return _params.isBoolean(); } @@ -140,6 +166,6 @@ bool AbstractFunction::checkCompatibility(const ParamType& _type, const ejson::V } return false; } -bool AbstractFunction::checkCompatibility(const ParamType& _type, const std::string& _params) { +bool jus::AbstractFunction::checkCompatibility(const ParamType& _type, const std::string& _params) { return false; } diff --git a/jus/AbstractFunction.h b/jus/AbstractFunction.h index c40723d..facae92 100644 --- a/jus/AbstractFunction.h +++ b/jus/AbstractFunction.h @@ -10,47 +10,42 @@ #include #include #include - -class AbstractFunction { - protected: - const std::string m_name; - public: - const std::string& getName() const { - return m_name; - } - protected: - const std::string m_description; - public: - const std::string& getDescription() const { - return m_description; - } - protected: - AbstractFunction(const std::string& _name, - const std::string& _desc): - m_name(_name), - m_description(_desc) { - - } - public: - virtual ~AbstractFunction() {}; - bool checkCompatibility(const ParamType& _type, const ejson::Value& _params); - bool checkCompatibility(const ParamType& _type, const std::string& _params); - public: - virtual std::string getPrototype() const = 0; - virtual ejson::Value executeJson(const ejson::Array& _params, void* _class=nullptr) = 0; - virtual std::string executeString(const std::vector& _params, void* _class=nullptr) = 0; -}; - -template -JUS_TYPE convertStringTo(const std::string& _value); - -template -JUS_TYPE convertJsonTo(const ejson::Value& _value); - -template -ejson::Value convertToJson(const JUS_TYPE& _value); -/* -template -class TypeList; -*/ +namespace jus { + class AbstractFunction { + protected: + std::string m_name; + public: + const std::string& getName() const; + protected: + std::string m_description; + public: + const std::string& getDescription() const; + void setDescription(const std::string& _desc); + protected: + std::vector> m_paramsDescription; + public: + void setParam(int32_t _idParam, const std::string& _name, const std::string& _desc); + void addParam(const std::string& _name, const std::string& _desc); + protected: + AbstractFunction(const std::string& _name, const std::string& _desc=""); + public: + virtual ~AbstractFunction() {}; + public: + bool checkCompatibility(const ParamType& _type, const ejson::Value& _params); + bool checkCompatibility(const ParamType& _type, const std::string& _params); + public: + virtual std::string getPrototype() const = 0; + virtual ejson::Value executeJson(const ejson::Array& _params, void* _class=nullptr) = 0; + virtual std::string executeString(const std::vector& _params, void* _class=nullptr) = 0; + }; + + template + JUS_TYPE convertStringTo(const std::string& _value); + + template + JUS_TYPE convertJsonTo(const ejson::Value& _value); + + template + ejson::Value convertToJson(const JUS_TYPE& _value); +} diff --git a/jus/AbstractFunctionTypeClass.h b/jus/AbstractFunctionTypeClass.h index 0c7850f..4f58b77 100644 --- a/jus/AbstractFunctionTypeClass.h +++ b/jus/AbstractFunctionTypeClass.h @@ -10,166 +10,167 @@ #include #include #include - -template -ejson::Value executeClassCallJson(JUS_CLASS_TYPE* _pointer, JUS_RETURN (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const ejson::Array& _params) { - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - return convertToJson((*_pointer.*_func)((convertJsonTo(_params[idParam++]))...)); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - return convertToJson((*_pointer.*_func)(convertJsonTo(_params[idParam--])...)); - #else - #error Must be implemented ... - #endif - return ejson::Null(); -} - -template -ejson::Value executeClassCallJson(JUS_CLASS_TYPE* _pointer, void (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const ejson::Array& _params) { - ejson::Object out; - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - (*_pointer.*_func)((convertJsonTo(_params[idParam++]))...); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - (*_pointer.*_func)(convertJsonTo(_params[idParam--])...); - #else - #error Must be implemented ... - #endif - return ejson::Null(); -} - -template -std::string executeClassCallString(JUS_CLASS_TYPE* _pointer, JUS_RETURN (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const std::vector& _params) { - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - return etk::to_string((*_pointer.*_func)((convertStringTo(_params[idParam++]))...)); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - return etk::to_string((*_pointer.*_func)(convertStringTo(_params[idParam--])...)); - #else - #error Must be implemented ... - #endif - return ""; -} -template -std::string executeClassCallString(JUS_CLASS_TYPE* _pointer, void (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const std::vector& _params) { - ejson::Object out; - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - (*_pointer.*_func)((convertStringTo(_params[idParam++]))...); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - (*_pointer.*_func)(convertStringTo(_params[idParam--])...); - #else - #error Must be implemented ... - #endif - return ""; -} - -template -class AbstractFunctionTypeClass: public AbstractFunction { - protected: - static const ParamType m_returnType; - static const ParamType m_paramType[sizeof...(JUS_TYPES)]; - public: - using functionType = JUS_RETURN (JUS_CLASS_TYPE::*)(JUS_TYPES...); - functionType m_function; - AbstractFunctionTypeClass(const std::string& _name, const std::string& _desc, functionType _fptr): - AbstractFunction(_name, _desc), - m_function(_fptr) { - } - std::string getPrototype() const override { - std::string ret; - ret += m_returnType.getName(); - ret += " "; - ret += m_name; - ret += "("; - for (size_t iii=0; iii + ejson::Value executeClassCallJson(JUS_CLASS_TYPE* _pointer, JUS_RETURN (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const ejson::Array& _params) { + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + return convertToJson((*_pointer.*_func)((convertJsonTo(_params[idParam++]))...)); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + return convertToJson((*_pointer.*_func)(convertJsonTo(_params[idParam--])...)); + #else + #error Must be implemented ... + #endif + return ejson::Null(); + } + + template + ejson::Value executeClassCallJson(JUS_CLASS_TYPE* _pointer, void (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const ejson::Array& _params) { + ejson::Object out; + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + (*_pointer.*_func)((convertJsonTo(_params[idParam++]))...); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + (*_pointer.*_func)(convertJsonTo(_params[idParam--])...); + #else + #error Must be implemented ... + #endif + return ejson::Null(); + } + + template + std::string executeClassCallString(JUS_CLASS_TYPE* _pointer, JUS_RETURN (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const std::vector& _params) { + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + return etk::to_string((*_pointer.*_func)((convertStringTo(_params[idParam++]))...)); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + return etk::to_string((*_pointer.*_func)(convertStringTo(_params[idParam--])...)); + #else + #error Must be implemented ... + #endif + return ""; + } + template + std::string executeClassCallString(JUS_CLASS_TYPE* _pointer, void (JUS_CLASS_TYPE::*_func)(JUS_TYPES...), const std::vector& _params) { + ejson::Object out; + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + (*_pointer.*_func)((convertStringTo(_params[idParam++]))...); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + (*_pointer.*_func)(convertStringTo(_params[idParam--])...); + #else + #error Must be implemented ... + #endif + return ""; + } + + template + class AbstractFunctionTypeClass: public jus::AbstractFunction { + protected: + static const ParamType m_returnType; + static const ParamType m_paramType[sizeof...(JUS_TYPES)]; + public: + using functionType = JUS_RETURN (JUS_CLASS_TYPE::*)(JUS_TYPES...); + functionType m_function; + AbstractFunctionTypeClass(const std::string& _name, const std::string& _desc, functionType _fptr): + AbstractFunction(_name, _desc), + m_function(_fptr) { + } + std::string getPrototype() const override { + std::string ret; + ret += m_returnType.getName(); + ret += " "; + ret += m_name; + ret += "("; + for (size_t iii=0; iii& _params, void* _class) override { - JUS_CLASS_TYPE* tmpClass = (JUS_CLASS_TYPE*)_class; - std::string out; - // check parameter number - if (_params.size() != sizeof...(JUS_TYPES)) { - JUS_ERROR("Wrong number of Parameters ..."); - out += "error:WRONG-PARAMETER-NUMBER;"; - out += "error-help:request "; - out += etk::to_string(_params.size()); - out += " parameters and need "; - out += etk::to_string(sizeof...(JUS_TYPES)); - out += " parameters. prototype function:"; - out += getPrototype(); + // check parameter compatibility + for (size_t iii=0; iii& _params, void* _class) override { + JUS_CLASS_TYPE* tmpClass = (JUS_CLASS_TYPE*)_class; + std::string out; + // check parameter number + if (_params.size() != sizeof...(JUS_TYPES)) { + JUS_ERROR("Wrong number of Parameters ..."); + out += "error:WRONG-PARAMETER-NUMBER;"; + out += "error-help:request "; + out += etk::to_string(_params.size()); + out += " parameters and need "; + out += etk::to_string(sizeof...(JUS_TYPES)); + out += " parameters. prototype function:"; + out += getPrototype(); return out; } + // check parameter compatibility + for (size_t iii=0; iii -const ParamType AbstractFunctionTypeClass::m_returnType = createType(); - -template -const ParamType AbstractFunctionTypeClass::m_paramType[sizeof...(JUS_TYPES)] = {createType()...}; - - -template -AbstractFunction* createAbstractFunctionClass(const std::string& _name, const std::string& _desc, JUS_RETURN (JUS_CLASS_TYPE::*_fffp)(JUS_TYPES...)) { - return new AbstractFunctionTypeClass(_name, _desc, _fffp); + }; + + template + const ParamType AbstractFunctionTypeClass::m_returnType = createType(); + + template + const ParamType AbstractFunctionTypeClass::m_paramType[sizeof...(JUS_TYPES)] = {createType()...}; + + + template + AbstractFunction* createAbstractFunctionClass(const std::string& _name, const std::string& _desc, JUS_RETURN (JUS_CLASS_TYPE::*_fffp)(JUS_TYPES...)) { + return new AbstractFunctionTypeClass(_name, _desc, _fffp); + } } diff --git a/jus/AbstractFunctionTypeDirect.h b/jus/AbstractFunctionTypeDirect.h index fc18f82..c323965 100644 --- a/jus/AbstractFunctionTypeDirect.h +++ b/jus/AbstractFunctionTypeDirect.h @@ -10,164 +10,164 @@ #include #include #include - -template -ejson::Value executeCallJson(JUS_RETURN (*_func)(JUS_TYPES...), const ejson::Array& _params) { - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - return convertToJson(_func((convertJsonTo(_params[idParam++]))...)); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - return convertToJson(_func(convertJsonTo(_params[idParam--])...)); - #else - #error Must be implemented ... - #endif - return ejson::Null(); -} - -template -ejson::Value executeCallJson(void (*_func)(JUS_TYPES...), const ejson::Array& _params) { - ejson::Object out; - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - _func((convertJsonTo(_params[idParam++]))...); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - _func(convertJsonTo(_params[idParam--])...); - #else - #error Must be implemented ... - #endif - return ejson::Null(); -} - -template -std::string executeCallString(JUS_RETURN (*_func)(JUS_TYPES...), const std::vector& _params) { - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - return etk::to_string(_func((convertStringTo(_params[idParam++]))...)); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - return etk::to_string(_func(convertStringTo(_params[idParam--])...)); - #else - #error Must be implemented ... - #endif - return ""; -} -template -std::string executeCallString(void (*_func)(JUS_TYPES...), const std::vector& _params) { - ejson::Object out; - #if defined(__clang__) - // clang generate a basic warning: - // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] - int32_t idParam = 0; - _func((convertStringTo(_params[idParam++]))...); - #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) - int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; - _func(convertStringTo(_params[idParam--])...); - #else - #error Must be implemented ... - #endif - return ""; -} - -template -class AbstractFunctionTypeDirect: public AbstractFunction { - protected: - static const ParamType m_returnType; - static const ParamType m_paramType[sizeof...(JUS_TYPES)]; - public: - using functionType = JUS_RETURN (*)(JUS_TYPES...); - functionType m_function; - AbstractFunctionTypeDirect(const std::string& _name, const std::string& _desc, functionType _fptr): - AbstractFunction(_name, _desc), - m_function(_fptr) { - } - std::string getPrototype() const override { - std::string ret; - ret += m_returnType.getName(); - ret += " "; - ret += m_name; - ret += "("; - for (size_t iii=0; iii + ejson::Value executeCallJson(JUS_RETURN (*_func)(JUS_TYPES...), const ejson::Array& _params) { + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + return convertToJson(_func((convertJsonTo(_params[idParam++]))...)); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + return convertToJson(_func(convertJsonTo(_params[idParam--])...)); + #else + #error Must be implemented ... + #endif + return ejson::Null(); + } + + template + ejson::Value executeCallJson(void (*_func)(JUS_TYPES...), const ejson::Array& _params) { + ejson::Object out; + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + _func((convertJsonTo(_params[idParam++]))...); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + _func(convertJsonTo(_params[idParam--])...); + #else + #error Must be implemented ... + #endif + return ejson::Null(); + } + + template + std::string executeCallString(JUS_RETURN (*_func)(JUS_TYPES...), const std::vector& _params) { + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + return etk::to_string(_func((convertStringTo(_params[idParam++]))...)); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + return etk::to_string(_func(convertStringTo(_params[idParam--])...)); + #else + #error Must be implemented ... + #endif + return ""; + } + template + std::string executeCallString(void (*_func)(JUS_TYPES...), const std::vector& _params) { + ejson::Object out; + #if defined(__clang__) + // clang generate a basic warning: + // warning: multiple unsequenced modifications to 'idParam' [-Wunsequenced] + int32_t idParam = 0; + _func((convertStringTo(_params[idParam++]))...); + #elif defined(__GNUC__) || defined(__GNUG__) || defined(_MSC_VER) + int32_t idParam = int32_t(sizeof...(JUS_TYPES))-1; + _func(convertStringTo(_params[idParam--])...); + #else + #error Must be implemented ... + #endif + return ""; + } + + template + class AbstractFunctionTypeDirect: public jus::AbstractFunction { + protected: + static const ParamType m_returnType; + static const ParamType m_paramType[sizeof...(JUS_TYPES)]; + public: + using functionType = JUS_RETURN (*)(JUS_TYPES...); + functionType m_function; + AbstractFunctionTypeDirect(const std::string& _name, const std::string& _desc, functionType _fptr): + AbstractFunction(_name, _desc), + m_function(_fptr) { + } + std::string getPrototype() const override { + std::string ret; + ret += m_returnType.getName(); + ret += " "; + ret += m_name; + ret += "("; + for (size_t iii=0; iii& _params, void* _class) override { - std::string out; - // check parameter number - if (_params.size() != sizeof...(JUS_TYPES)) { - JUS_ERROR("Wrong number of Parameters ..."); - out += "error:WRONG-PARAMETER-NUMBER;"; - out += "error-help:request "; - out += etk::to_string(_params.size()); - out += " parameters and need "; - out += etk::to_string(sizeof...(JUS_TYPES)); - out += " parameters. prototype function:"; - out += getPrototype(); + // check parameter compatibility + for (size_t iii=0; iii& _params, void* _class) override { + std::string out; + // check parameter number + if (_params.size() != sizeof...(JUS_TYPES)) { + JUS_ERROR("Wrong number of Parameters ..."); + out += "error:WRONG-PARAMETER-NUMBER;"; + out += "error-help:request "; + out += etk::to_string(_params.size()); + out += " parameters and need "; + out += etk::to_string(sizeof...(JUS_TYPES)); + out += " parameters. prototype function:"; + out += getPrototype(); return out; } + // check parameter compatibility + for (size_t iii=0; iii -const ParamType AbstractFunctionTypeDirect::m_returnType = createType(); - -template -const ParamType AbstractFunctionTypeDirect::m_paramType[sizeof...(JUS_TYPES)] = {createType()...}; - - -template -AbstractFunction* createAbstractFunctionDirect(const std::string& _name, const std::string& _desc, JUS_RETURN (*_fffp)(JUS_TYPES...)) { - return new AbstractFunctionTypeDirect(_name, _desc, _fffp); + }; + + template + const ParamType AbstractFunctionTypeDirect::m_returnType = createType(); + + template + const ParamType AbstractFunctionTypeDirect::m_paramType[sizeof...(JUS_TYPES)] = {createType()...}; + + + template + AbstractFunction* createAbstractFunctionDirect(const std::string& _name, const std::string& _desc, JUS_RETURN (*_fffp)(JUS_TYPES...)) { + return new AbstractFunctionTypeDirect(_name, _desc, _fffp); + } } - diff --git a/jus/Client.cpp b/jus/Client.cpp index 2972063..1dd4ac8 100644 --- a/jus/Client.cpp +++ b/jus/Client.cpp @@ -45,6 +45,9 @@ void jus::Client::unlink(const std::string& _serviceName) { } std::string jus::Client::asyncRead() { + if (m_interfaceClient.isActive() == false) { + return ""; + } int32_t iii = 5000; while (iii>0) { usleep(10000); @@ -102,9 +105,11 @@ ejson::Object jus::Client::createBaseCall(const std::string& _functionName, cons ejson::Object jus::Client::callJson(const ejson::Object& _obj) { JUS_VERBOSE("Call JSON [START] "); - std::string tmpVal = _obj.generate(); - JUS_DEBUG("Call JSON '" << tmpVal << "'"); - m_interfaceClient.write(_obj.generate()); + if (m_interfaceClient.isActive() == false) { + return ejson::Object(); + } + JUS_DEBUG("Call JSON '" << _obj.generateHumanString() << "'"); + m_interfaceClient.write(_obj.generateMachineString()); std::string ret = asyncRead(); JUS_VERBOSE("Call JSON [STOP]"); return ejson::Object(ret); diff --git a/jus/GateWay.cpp b/jus/GateWay.cpp index e1331ba..ad928f6 100644 --- a/jus/GateWay.cpp +++ b/jus/GateWay.cpp @@ -130,6 +130,37 @@ void jus::GateWay::answer(uint64_t _userSessionId, ejson::Object _data) { } } +void jus::GateWay::cleanIO() { + + auto it = m_serviceList.begin(); + while (it != m_serviceList.end()) { + if (*it != nullptr) { + if ((*it)->isAlive() == false) { + it = m_serviceList.erase(it); + continue; + } + } else { + it = m_serviceList.erase(it); + continue; + } + ++it; + } + + auto it2 = m_clientList.begin(); + while (it2 != m_clientList.end()) { + if (*it2 != nullptr) { + if ((*it2)->isAlive() == false) { + it2 = m_clientList.erase(it2); + continue; + } + } else { + it2 = m_clientList.erase(it2); + continue; + } + ++it2; + } +} + void jus::GateWay::onClientConnect(const bool& _value) { JUS_TODO("Client connection: " << _value); } diff --git a/jus/GateWay.h b/jus/GateWay.h index 6a4994f..c6ad05b 100644 --- a/jus/GateWay.h +++ b/jus/GateWay.h @@ -35,6 +35,7 @@ namespace jus { void answer(uint64_t _userSessionId, ejson::Object _data); void newService(enet::Tcp _connection); void newClient(enet::Tcp _connection); + void cleanIO(); private: void onPropertyChangeClientIp(); void onPropertyChangeClientPort(); diff --git a/jus/GateWayClient.cpp b/jus/GateWayClient.cpp index d43de47..13fe29b 100644 --- a/jus/GateWayClient.cpp +++ b/jus/GateWayClient.cpp @@ -12,14 +12,18 @@ jus::GateWayClient::GateWayClient(enet::Tcp _connection, jus::GateWay* _gatewayInterface) : m_gatewayInterface(_gatewayInterface), - m_interfaceClient(std::move(_connection)), - m_returnValueOk(false) { - + m_interfaceClient(std::move(_connection)) { + JUS_INFO("----------------"); + JUS_INFO("-- NEW Client --"); + JUS_INFO("----------------"); } jus::GateWayClient::~GateWayClient() { JUS_TODO("Call All unlink ..."); - + stop(); + JUS_INFO("-------------------"); + JUS_INFO("-- DELETE Client --"); + JUS_INFO("-------------------"); } void jus::GateWayClient::start(size_t _uid) { @@ -30,9 +34,20 @@ void jus::GateWayClient::start(size_t _uid) { } void jus::GateWayClient::stop() { + for (auto &it : m_listConnectedService) { + if (it == nullptr) { + continue; + } + it->SendData(m_uid, ejson::Object(), "delete"); + } + m_listConnectedService.clear(); m_interfaceClient.disconnect(); } +bool jus::GateWayClient::isAlive() { + return m_interfaceClient.isActive(); +} + void jus::GateWayClient::onClientData(const std::string& _value) { JUS_DEBUG("On data: " << _value); ejson::Object data(_value); @@ -93,18 +108,8 @@ void jus::GateWayClient::onClientData(const std::string& _value) { ejson::Object linkService; linkService.add("user", ejson::String(m_userConnectionName)); srv->SendData(m_uid, linkService, "new"); - while (m_returnValueOk == false) { - JUS_DEBUG("wait Return Value (LINK)"); - usleep(20000); - } - JUS_DEBUG("new answer: " << m_returnMessage.generate()); - if (m_returnMessage["return"].toString().get() == "OK") { - m_listConnectedService.push_back(srv); - answer.add("return", ejson::Boolean(true)); - } else { - answer.add("return", ejson::Boolean(false)); - } - m_returnValueOk = false; + m_listConnectedService.push_back(srv); + answer.add("return", ejson::Boolean(true)); } else { answer.add("return", ejson::Boolean(false)); } @@ -129,30 +134,18 @@ void jus::GateWayClient::onClientData(const std::string& _value) { break; } if (it == m_listConnectedService.end()) { - // TODO : Service already unlink; answer.add("return", ejson::Boolean(false)); } else { (*it)->SendData(m_uid, ejson::Object(), "delete"); - while (m_returnValueOk == false) { - JUS_DEBUG("wait Return Value (UNLINK)"); - usleep(20000); - } - JUS_DEBUG("new answer: " << m_returnMessage.generate()); - if (m_returnMessage["return"].toString().get() == "OK") { - m_listConnectedService.erase(it); - answer.add("return", ejson::Boolean(true)); - } else { - answer.add("return", ejson::Boolean(false)); - } - m_returnValueOk = false; + m_listConnectedService.erase(it); + answer.add("return", ejson::Boolean(true)); } } else { JUS_ERROR("Function does not exist ... '" << call << "'"); answer.add("error", ejson::String("CALL-UNEXISTING")); } - std::string valueReturn = answer.generate(); - JUS_DEBUG("answer: " << valueReturn); - m_interfaceClient.write(valueReturn); + JUS_DEBUG("answer: " << answer.generateHumanString()); + m_interfaceClient.write(answer.generateMachineString()); } else if (service == "Authentification") { std::string call = data["call"].toString().get(); @@ -176,26 +169,17 @@ void jus::GateWayClient::onClientData(const std::string& _value) { answer.add("id", data["id"]); JUS_ERROR("Service not linked ... " << service); answer.add("error", ejson::String("SERVICE-NOT-LINK")); - std::string valueReturn = answer.generate(); - JUS_DEBUG("answer: " << valueReturn); - m_interfaceClient.write(valueReturn); + JUS_DEBUG("answer: " << answer.generateHumanString()); + m_interfaceClient.write(answer.generateMachineString()); } else { JUS_ERROR("Add in link the name of the user in parameter ..."); data.remove("service"); (*it)->SendData(m_uid, data); - while (m_returnValueOk == false) { - JUS_DEBUG("wait Return Value"); - usleep(20000); - } - std::string valueReturn = m_returnMessage.generate(); - JUS_DEBUG("answer: " << valueReturn); - m_interfaceClient.write(valueReturn); - m_returnValueOk = false; } } } void jus::GateWayClient::returnMessage(ejson::Object _data) { - m_returnMessage = _data; - m_returnValueOk = true; + JUS_DEBUG("answer: " << _data.generateHumanString()); + m_interfaceClient.write(_data.generateMachineString()); } \ No newline at end of file diff --git a/jus/GateWayClient.h b/jus/GateWayClient.h index 972d79f..fb002cd 100644 --- a/jus/GateWayClient.h +++ b/jus/GateWayClient.h @@ -19,8 +19,6 @@ namespace jus { public: esignal::Signal signalIsConnected; esignal::Connection m_dataCallback; - bool m_returnValueOk; - ejson::Object m_returnMessage; std::vector> m_listConnectedService; size_t m_uid; std::string m_userConnectionName; @@ -34,6 +32,7 @@ namespace jus { size_t getId() const { return m_uid; } + bool isAlive(); }; } diff --git a/jus/GateWayService.cpp b/jus/GateWayService.cpp index 670fb02..a936e8c 100644 --- a/jus/GateWayService.cpp +++ b/jus/GateWayService.cpp @@ -12,11 +12,20 @@ jus::GateWayService::GateWayService(enet::Tcp _connection, jus::GateWay* _gatewayInterface) : m_gatewayInterface(_gatewayInterface), m_interfaceClient(std::move(_connection)) { - + JUS_INFO("-----------------"); + JUS_INFO("-- NEW Service --"); + JUS_INFO("-----------------"); } jus::GateWayService::~GateWayService() { + JUS_INFO("--------------------"); + JUS_INFO("-- DELETE Service --"); + JUS_INFO("--------------------"); +} + +bool jus::GateWayService::isAlive() { + return m_interfaceClient.isActive(); } void jus::GateWayService::start() { @@ -32,14 +41,21 @@ void jus::GateWayService::stop() { void jus::GateWayService::SendData(size_t _userSessionId, ejson::Object _data, const std::string& _action) { _data.add("client-id", ejson::String(etk::to_string(_userSessionId))); _data.add("action", ejson::String(_action)); - std::string value = _data.generate(); - JUS_DEBUG("Send Service: " << value); - m_interfaceClient.write(value); + JUS_DEBUG("Send Service: " << _data.generateHumanString()); + m_interfaceClient.write(_data.generateMachineString()); } void jus::GateWayService::onServiceData(const std::string& _value) { JUS_DEBUG("On service data: " << _value); ejson::Object data(_value); + if (data.valueExist("event") == true) { + if (data["event"].toString().get() == "IS-ALIVE") { + JUS_INFO("Service Alive ..."); + } else { + JUS_INFO("Unknow service event: '" << data["event"].toString().get() << "'"); + } + return; + } if (data.valueExist("connect-service") == true) { if (m_name != "") { JUS_WARNING("Service interface ==> try change the servie name after init: '" << data["connect-service"].toString().get()); diff --git a/jus/GateWayService.h b/jus/GateWayService.h index 568c5c9..7ef9a6f 100644 --- a/jus/GateWayService.h +++ b/jus/GateWayService.h @@ -31,6 +31,7 @@ namespace jus { const std::string& getName() { return m_name; } + bool isAlive(); }; } diff --git a/jus/ParamType.cpp b/jus/ParamType.cpp index cf2d9ef..74a4325 100644 --- a/jus/ParamType.cpp +++ b/jus/ParamType.cpp @@ -23,8 +23,8 @@ bool jus::ParamType::operator == (const ParamType& _obj) const { #define generate_basic_type(_type, _name) \ -template<> ParamType createType<_type>() {\ - return ParamType(_name); \ +template<> jus::ParamType jus::createType<_type>() {\ + return jus::ParamType(_name); \ } generate_basic_type(void, "void"); diff --git a/jus/ParamType.h b/jus/ParamType.h index 4a416a1..f88b626 100644 --- a/jus/ParamType.h +++ b/jus/ParamType.h @@ -4,18 +4,18 @@ * @license APACHE v2.0 (see license file) */ #pragma once - -class ParamType { - protected: - const char* m_typeName; - public: - ParamType(const char* _name = ""); - const char* getName() const; - bool operator == (const ParamType& _obj) const; -}; - - -template -ParamType createType(); - +namespace jus { + class ParamType { + protected: + const char* m_typeName; + public: + ParamType(const char* _name = ""); + const char* getName() const; + bool operator == (const ParamType& _obj) const; + }; + + + template + ParamType createType(); +} diff --git a/jus/RemoteProcessCall.cpp b/jus/RemoteProcessCall.cpp new file mode 100644 index 0000000..1cd9450 --- /dev/null +++ b/jus/RemoteProcessCall.cpp @@ -0,0 +1,86 @@ +/** @file + * @author Edouard DUPIN + * @copyright 2016, Edouard DUPIN, all right reserved + * @license APACHE v2.0 (see license file) + */ +#include + + +std::vector m_listFunction; + + +void jus::RemoteProcessCall::setDescription(const std::string& _desc) { + m_description = _desc; +} + +const std::string& jus::RemoteProcessCall::getDescription() const { + return m_description; +} + +void jus::RemoteProcessCall::setVersion(const std::string& _desc) { + m_version = _desc; +} + +const std::string& jus::RemoteProcessCall::getVersion() const { + return m_version; +} + +void jus::RemoteProcessCall::addAuthor(const std::string& _name, const std::string& _email) { + m_authors.push_back(std::make_pair(_name, _email)); +} + +const std::vector>& jus::RemoteProcessCall::getAuthors() const { + return m_authors; +} + +void jus::RemoteProcessCall::setLastFuncDesc(const std::string& _desc) { + if (m_listFunction.size() == 0) { + JUS_ERROR("Can not set description to a function with no function advertise before ..."); + return; + } + if (m_listFunction[m_listFunction.size()-1] == nullptr) { + JUS_ERROR("Last element is nullptr ... ==> what are you doing??"); + return; + } + m_listFunction[m_listFunction.size()-1]->setDescription(_desc); +} + +void jus::RemoteProcessCall::setFuncDesc(const std::string& _funcName, const std::string& _desc) { + for (auto &it : m_listFunction) { + if (it == nullptr) { + continue; + } + if (it->getName() != _funcName) { + continue; + } + it->setDescription(_desc); + return; + } + JUS_ERROR("function '" << _funcName << "' des not exist"); +} + +void jus::RemoteProcessCall::addLastFuncParam(const std::string& _name, const std::string& _desc) { + if (m_listFunction.size() == 0) { + JUS_ERROR("Can not set description to a function with no function advertise before ..."); + return; + } + if (m_listFunction[m_listFunction.size()-1] == nullptr) { + JUS_ERROR("Last element is nullptr ... ==> what are you doing??"); + return; + } + m_listFunction[m_listFunction.size()-1]->addParam(_name, _desc); +} + +void jus::RemoteProcessCall::setFuncParam(const std::string& _funcName, int32_t _idParam, const std::string& _name, const std::string& _desc) { + for (auto &it : m_listFunction) { + if (it == nullptr) { + continue; + } + if (it->getName() != _funcName) { + continue; + } + it->setParam(_idParam, _name, _desc); + return; + } + JUS_ERROR("function '" << _funcName << "' des not exist"); +} diff --git a/jus/RemoteProcessCall.h b/jus/RemoteProcessCall.h new file mode 100644 index 0000000..79c783a --- /dev/null +++ b/jus/RemoteProcessCall.h @@ -0,0 +1,59 @@ +/** @file + * @author Edouard DUPIN + * @copyright 2016, Edouard DUPIN, all right reserved + * @license APACHE v2.0 (see license file) + */ +#pragma once + +#include +#include +#include +#include +#include +#include + +namespace jus { + class RemoteProcessCall { + protected: + std::vector m_listFunction; + protected: + std::string m_description; + public: + void setDescription(const std::string& _desc); + const std::string& getDescription() const; + protected: + std::string m_version; + public: + void setVersion(const std::string& _desc); + const std::string& getVersion() const; + protected: + std::vector> m_authors; + public: + void addAuthor(const std::string& _name, const std::string& _email); + const std::vector>& getAuthors() const; + public: + void setLastFuncDesc(const std::string& _desc); + void setFuncDesc(const std::string& _funcName, const std::string& _desc); + void addLastFuncParam(const std::string& _name, const std::string& _desc); + void setFuncParam(const std::string& _funcName, int32_t _idParam, const std::string& _name, const std::string& _desc); + public: + template + void advertise(const std::string& _name, + JUS_RETURN_VALUE (*_func)(JUS_FUNC_ARGS_TYPE... _args), + const std::string& _desc = "") { + for (auto &it : m_listFunction) { + if (it == nullptr) { + continue; + } + if (it->getName() == _name) { + JUS_ERROR("Advertise function already bind .. ==> can not be done...: '" << _name << "'"); + return; + } + } + AbstractFunction* tmp = createAbstractFunctionDirect(_name, _desc, _func); + m_listFunction.push_back(tmp); + } + }; +} + diff --git a/jus/Service.cpp b/jus/Service.cpp index ddc9453..ce4a637 100644 --- a/jus/Service.cpp +++ b/jus/Service.cpp @@ -27,10 +27,12 @@ jus::Service::~Service() { void jus::Service::onClientData(const std::string& _value) { ejson::Object request(_value); JUS_INFO("Request: " << _value); - ejson::Object answer = callJson(request); - std::string answerString = answer.generate(); - JUS_INFO("Answer: " << answerString); - m_interfaceClient.write(answerString); + ejson::Value answer = callJson(request); + // check if an answer is needed + if (answer.isNull() == false) { + JUS_INFO("Answer: " << answer.generateHumanString()); + m_interfaceClient.write(answer.generateMachineString()); + } } void jus::Service::onPropertyChangeIp() { @@ -58,33 +60,44 @@ void jus::Service::disconnect(){ JUS_DEBUG("disconnect [STOP]"); } -ejson::Object jus::Service::callJson(const ejson::Object& _obj) { + +void jus::Service::pingIsAlive() { + m_interfaceClient.write("{\"event\":\"IS-ALIVE\"}"); +} + +ejson::Value jus::Service::callJson(const ejson::Object& _obj) { std::string action = _obj["action"].toString().get(); if (action == "new") { uint64_t clientId = etk::string_to_uint64_t(_obj["client-id"].toString().get()); std::string userName = _obj["user"].toString().get(); clientConnect(clientId, userName); + /* ejson::Object tmpp; tmpp.add("client-id", ejson::String(etk::to_string(clientId))); tmpp.add("return", ejson::String("OK")); - return tmpp; - } else if (action == "delete") { + return tmpp + */ + return ejson::Null(); + } + if (action == "delete") { uint64_t clientId = etk::string_to_uint64_t(_obj["client-id"].toString().get()); clientDisconnect(clientId); + /* ejson::Object tmpp; tmpp.add("client-id", ejson::String(etk::to_string(clientId))); tmpp.add("return", ejson::String("OK")); return tmpp; - } else if ( action == "call" - || action == "") { + */ + return ejson::Null(); + } + if ( action == "call" + || action == "") { uint64_t clientId = etk::string_to_uint64_t(_obj["client-id"].toString().get()); ejson::Object tmpp = callJson2(clientId, _obj); tmpp.add("client-id", ejson::String(etk::to_string(clientId))); return tmpp; - } else { - ejson::Object tmpp; - tmpp.add("error", ejson::String("NOT-IMPLEMENTED-ACTION")); - return tmpp; } - return ejson::Object(); + ejson::Object tmpp; + tmpp.add("error", ejson::String("NOT-IMPLEMENTED-ACTION")); + return tmpp; } diff --git a/jus/Service.h b/jus/Service.h index 15be257..bbd25af 100644 --- a/jus/Service.h +++ b/jus/Service.h @@ -11,9 +11,10 @@ #include #include #include +#include namespace jus { - class Service : public eproperty::Interface { + class Service : public eproperty::Interface, public jus::RemoteProcessCall { public: eproperty::Value propertyIp; eproperty::Value propertyPort; @@ -25,25 +26,16 @@ namespace jus { public: Service(); virtual ~Service(); - // Genenric function call: - ejson::Object callJson(const ejson::Object& _obj); - virtual ejson::Object callJson2(size_t _clientId, const ejson::Object& _obj) = 0; void connect(const std::string& _serviceName); void disconnect(); private: void onClientData(const std::string& _value); std::string asyncRead(); + public: + void pingIsAlive(); private: void onPropertyChangeIp(); void onPropertyChangePort(); - public: - template - void advertise(const std::string& _name, - JUS_RETURN_VALUE (*_func)(JUS_FUNC_ARGS_TYPE... _args), - const std::string& _desc) { - AbstractFunction* tmp = createAbstractFunctionDirect(_name, _desc, _func); - } /** * @brief A extern client connect on specific user * @param[in] _clientSessionID Source session Id on the client @@ -52,6 +44,9 @@ namespace jus { */ virtual void clientConnect(size_t _clientSessionID, const std::string& _userName) = 0; virtual void clientDisconnect(size_t _clientSessionID) = 0; + // Genenric function call: + ejson::Value callJson(const ejson::Object& _obj); + virtual ejson::Object callJson2(size_t _clientId, const ejson::Object& _obj) = 0; }; template class ServiceType : public jus::Service { @@ -59,15 +54,23 @@ namespace jus { JUS_USER_ACCESS& m_getUserInterface; // no need of shared_ptr or unique_ptr (if service die all is lost and is client die, the gateway notify us...) std::map m_interface; - std::vector m_listFunction; + public: template void advertise(const std::string& _name, JUS_RETURN_VALUE (JUS_CLASS_TYPE::*_func)(JUS_FUNC_ARGS_TYPE... _args), - const std::string& _desc) { - // TODO: check if fucntion does not exist ... + const std::string& _desc = "") { + for (auto &it : m_listFunction) { + if (it == nullptr) { + continue; + } + if (it->getName() == _name) { + JUS_ERROR("Advertise function already bind .. ==> can not be done...: '" << _name << "'"); + return; + } + } AbstractFunction* tmp = createAbstractFunctionClass(_name, _desc, _func); m_listFunction.push_back(tmp); } diff --git a/jus/TcpString.cpp b/jus/TcpString.cpp index fa7ef06..62b424c 100644 --- a/jus/TcpString.cpp +++ b/jus/TcpString.cpp @@ -48,9 +48,14 @@ void jus::TcpString::threadCallback() { signalData.emit(data); } } + m_threadRunning = false; JUS_DEBUG("End of thread"); } +bool jus::TcpString::isActive() const { + return m_threadRunning; +} + void jus::TcpString::connect(bool _async){ JUS_DEBUG("connect [START]"); m_threadRunning = true; @@ -75,13 +80,13 @@ void jus::TcpString::connect(bool _async){ void jus::TcpString::disconnect(){ JUS_DEBUG("disconnect [START]"); + if (m_thread != nullptr) { + m_threadRunning = false; + } if (m_connection.getConnectionStatus() == enet::Tcp::status::link) { uint32_t size = 0xFFFFFFFF; m_connection.write(&size, 4); } - if (m_thread != nullptr) { - m_threadRunning = false; - } if (m_connection.getConnectionStatus() != enet::Tcp::status::unlink) { m_connection.unlink(); } @@ -94,6 +99,9 @@ void jus::TcpString::disconnect(){ } int32_t jus::TcpString::write(const std::string& _data) { + if (m_threadRunning == false) { + return -2; + } if (_data.size() == 0) { return 0; } @@ -103,6 +111,11 @@ int32_t jus::TcpString::write(const std::string& _data) { } std::string jus::TcpString::read() { + JUS_VERBOSE("Read [START]"); + if (m_threadRunning == false) { + JUS_DEBUG("Read [END] Disconected"); + return ""; + } // TODO : Do it better with a correct way to check data size ... JUS_VERBOSE("Read [START]"); std::string out; diff --git a/jus/TcpString.h b/jus/TcpString.h index a83b53b..b7408ba 100644 --- a/jus/TcpString.h +++ b/jus/TcpString.h @@ -26,6 +26,7 @@ namespace jus { void setInterface(enet::Tcp _connection); void connect(bool _async = false); void disconnect(); + bool isActive() const; void setInterfaceName(const std::string& _name); int32_t write(const std::string& _data); std::string asyncRead(); diff --git a/lutin_jus.py b/lutin_jus.py index 21d5292..5e337e5 100644 --- a/lutin_jus.py +++ b/lutin_jus.py @@ -40,6 +40,7 @@ def create(target, module_name): 'jus/GateWay.cpp', 'jus/GateWayService.cpp', 'jus/GateWayClient.cpp', + 'jus/RemoteProcessCall.cpp', 'jus/Service.cpp', 'jus/ServiceRemote.cpp', 'jus/TcpString.cpp', @@ -54,6 +55,7 @@ def create(target, module_name): 'jus/GateWay.h', 'jus/GateWayService.h', 'jus/GateWayClient.h', + 'jus/RemoteProcessCall.h', 'jus/Service.h', 'jus/ServiceRemote.h', 'jus/TcpString.h', diff --git a/test/service1/appl/main.cpp b/test/service1/appl/main.cpp index 39dc311..7981d62 100644 --- a/test/service1/appl/main.cpp +++ b/test/service1/appl/main.cpp @@ -69,7 +69,13 @@ int main(int _argc, const char *_argv[]) { etk::init(_argc, _argv); appl::UserManager userMng; jus::ServiceType serviceInterface(userMng); - serviceInterface.advertise("mul", &appl::Calculator::mul, "simple multiplication to test double IO"); + serviceInterface.setDescription("Calculator interface"); + serviceInterface.setVersion("0.1.1"); + serviceInterface.addAuthor("Heero Yui", "yui.heero@gmail.com"); + serviceInterface.advertise("mul", &appl::Calculator::mul); + serviceInterface.setLastFuncDesc("simple multiplication to test double IO"); + serviceInterface.addLastFuncParam("val1", "First Parameter To multiply"); + serviceInterface.addLastFuncParam("val2", "Second Parameter To multiply"); for (int32_t iii=0; iii<_argc ; ++iii) { std::string data = _argv[iii]; if (etk::start_with(data, "--ip=") == true) { @@ -91,7 +97,8 @@ int main(int _argc, const char *_argv[]) { serviceInterface.connect("serviceTest1"); int32_t iii=0; while (true) { - usleep(500000); + usleep(1000000); + serviceInterface.pingIsAlive(); APPL_INFO("service in waiting ... " << iii << "/inf"); iii++; } diff --git a/tools/gateway/appl/main.cpp b/tools/gateway/appl/main.cpp index 4a512d3..1d6a1f8 100644 --- a/tools/gateway/appl/main.cpp +++ b/tools/gateway/appl/main.cpp @@ -46,8 +46,10 @@ int main(int _argc, const char *_argv[]) { APPL_INFO("=================================="); basicGateway.start(); while (true) { - usleep(200000); + usleep(100000); + basicGateway.cleanIO(); } + basicGateway.stop(); APPL_INFO("=================================="); APPL_INFO("== JUS gateway stop =="); APPL_INFO("==================================");