1 /*****************************************************************
3 | Platinum - Service State Variable
5 | Copyright (c) 2004-2010, Plutinosoft, LLC.
7 | http://www.plutinosoft.com
9 | This program is free software; you can redistribute it and/or
10 | modify it under the terms of the GNU General Public License
11 | as published by the Free Software Foundation; either version 2
12 | of the License, or (at your option) any later version.
14 | OEMs, ISVs, VARs and other distributors that combine and
15 | distribute commercially licensed software with Platinum software
16 | and do not wish to distribute the source code for the commercially
17 | licensed software under version 2, or (at your option) any later
18 | version, of the GNU General Public License (the "GPL") must enter
19 | into a commercial license agreement with Plutinosoft, LLC.
20 | licensing@plutinosoft.com
22 | This program is distributed in the hope that it will be useful,
23 | but WITHOUT ANY WARRANTY; without even the implied warranty of
24 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
25 | GNU General Public License for more details.
27 | You should have received a copy of the GNU General Public License
28 | along with this program; see the file LICENSE.txt. If not, write to
29 | the Free Software Foundation, Inc.,
30 | 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
31 | http://www.gnu.org/licenses/gpl-2.0.html
33 ****************************************************************/
35 /*----------------------------------------------------------------------
37 +---------------------------------------------------------------------*/
38 #include "PltStateVariable.h"
39 #include "PltService.h"
40 #include "PltUtilities.h"
43 NPT_SET_LOCAL_LOGGER("platinum.core.statevariable")
45 /*----------------------------------------------------------------------
46 | PLT_StateVariable::PLT_StateVariable
47 +---------------------------------------------------------------------*/
48 PLT_StateVariable::PLT_StateVariable(PLT_Service
* service
) :
50 m_AllowedValueRange(NULL
),
51 m_IsSendingEvents(false),
52 m_IsSendingEventsIndirectly(true),
53 m_ShouldClearOnSend(false)
57 /*----------------------------------------------------------------------
58 | PLT_StateVariable::~PLT_StateVariable
59 +---------------------------------------------------------------------*/
60 PLT_StateVariable::~PLT_StateVariable()
62 m_AllowedValues
.Apply(NPT_ObjectDeleter
<NPT_String
>());
63 if (m_AllowedValueRange
) delete m_AllowedValueRange
;
66 /*----------------------------------------------------------------------
67 | PLT_StateVariable::GetSCPDXML
68 +---------------------------------------------------------------------*/
70 PLT_StateVariable::GetSCPDXML(NPT_XmlElementNode
* node
)
72 NPT_XmlElementNode
* variable
= new NPT_XmlElementNode("stateVariable");
73 NPT_CHECK_SEVERE(node
->AddChild(variable
));
75 NPT_CHECK_SEVERE(variable
->SetAttribute("sendEvents", m_IsSendingEvents
?"yes":"no"));
76 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(variable
, "name", m_Name
));
77 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(variable
, "dataType", m_DataType
));
78 if (m_DefaultValue
.GetLength()) {
79 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(variable
, "defaultValue", m_DefaultValue
));
82 if (m_AllowedValues
.GetItemCount()) {
83 NPT_XmlElementNode
* allowedValueList
= new NPT_XmlElementNode("allowedValueList");
84 NPT_CHECK_SEVERE(variable
->AddChild(allowedValueList
));
85 for( int l
= 0 ; l
< (int)m_AllowedValues
.GetItemCount(); l
++) {
86 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(allowedValueList
, "allowedValue", (*m_AllowedValues
[l
])));
88 } else if (m_AllowedValueRange
) {
89 NPT_XmlElementNode
* range
= new NPT_XmlElementNode("allowedValueRange");
90 NPT_CHECK_SEVERE(variable
->AddChild(range
));
91 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(range
, "minimum", NPT_String::FromInteger(m_AllowedValueRange
->min_value
)));
92 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(range
, "maximum", NPT_String::FromInteger(m_AllowedValueRange
->max_value
)));
93 if (m_AllowedValueRange
->step
!= -1) {
94 NPT_CHECK_SEVERE(PLT_XmlHelper::AddChildText(range
, "step", NPT_String::FromInteger(m_AllowedValueRange
->step
)));
101 /*----------------------------------------------------------------------
102 | PLT_StateVariable::GetService
103 +---------------------------------------------------------------------*/
105 PLT_StateVariable::GetService()
110 /*----------------------------------------------------------------------
111 | PLT_StateVariable::IsSendingEvents
112 +---------------------------------------------------------------------*/
114 PLT_StateVariable::IsSendingEvents(bool indirectly
/* = false */)
117 return (!m_IsSendingEvents
&&
118 !m_Name
.StartsWith("A_ARG_TYPE_") &&
119 m_IsSendingEventsIndirectly
);
122 return m_IsSendingEvents
;
125 /*----------------------------------------------------------------------
126 | PLT_StateVariable::DisableIndirectEventing
127 +---------------------------------------------------------------------*/
129 PLT_StateVariable::DisableIndirectEventing()
131 m_IsSendingEventsIndirectly
= false;
134 /*----------------------------------------------------------------------
135 | PLT_StateVariable::SetRate
136 +---------------------------------------------------------------------*/
138 PLT_StateVariable::SetRate(NPT_TimeInterval rate
)
140 if (!IsSendingEvents()) return NPT_FAILURE
;
146 /*----------------------------------------------------------------------
147 | PLT_StateVariable::SetValue
148 +---------------------------------------------------------------------*/
150 PLT_StateVariable::SetValue(const char* value
, const bool clearonsend
/*=false*/)
156 // update only if it's different
157 if (m_Value
!= value
) {
158 NPT_Result res
= ValidateValue(value
);
159 if (NPT_FAILED(res
)) {
164 m_ShouldClearOnSend
= clearonsend
;
165 m_Service
->AddChanged(this);
171 /*----------------------------------------------------------------------
172 | PLT_StateVariable::IsReadyToPublish
173 +---------------------------------------------------------------------*/
175 PLT_StateVariable::IsReadyToPublish()
178 NPT_System::GetCurrentTimeStamp(now
);
180 if (m_Rate
== NPT_TimeStamp() || m_LastEvent
+ m_Rate
<= now
) {
188 /*----------------------------------------------------------------------
189 | PLT_StateVariable::OnSendCompleted
190 +---------------------------------------------------------------------*/
192 PLT_StateVariable::OnSendCompleted()
194 if(m_ShouldClearOnSend
)
195 m_Value
= m_DefaultValue
;
198 /*----------------------------------------------------------------------
199 | PLT_StateVariable::ValidateValue
200 +---------------------------------------------------------------------*/
202 PLT_StateVariable::ValidateValue(const char* value
)
204 if (m_DataType
.Compare("string", true) == 0) {
205 // if we have a value allowed restriction, make sure the value is in our list
206 if (m_AllowedValues
.GetItemCount()) {
207 // look for a comma separated list
208 NPT_String _value
= value
;
209 NPT_List
<NPT_String
> values
= _value
.Split(",");
210 NPT_List
<NPT_String
>::Iterator val
= values
.GetFirstItem();
213 if (!m_AllowedValues
.Find(NPT_StringFinder(*val
))) {
214 #if defined(NPT_CONFIG_ENABLE_LOGGING)
215 NPT_LOG_WARNING_2("Invalid value of %s for state variable %s",
217 (const char*)m_Name
);
218 for (unsigned long i
=0; i
< m_AllowedValues
.GetItemCount(); i
++) {
219 NPT_String
*val2
= *m_AllowedValues
.GetItem(i
);
220 NPT_LOG_WARNING_1("Allowed: %s", (const char*)*val2
);
223 return NPT_ERROR_INVALID_PARAMETERS
;
230 // TODO: there are more to it than allowed values, we need to test for range, etc..
234 /*----------------------------------------------------------------------
235 | PLT_StateVariable::Find
236 +---------------------------------------------------------------------*/
238 PLT_StateVariable::Find(NPT_List
<PLT_StateVariable
*>& vars
, const char* name
)
240 PLT_StateVariable
* stateVariable
= NULL
;
241 NPT_ContainerFind(vars
, PLT_StateVariableNameFinder(name
), stateVariable
);
242 return stateVariable
;
245 /*----------------------------------------------------------------------
246 | PLT_StateVariable::SetExtraAttribute
247 +---------------------------------------------------------------------*/
249 PLT_StateVariable::SetExtraAttribute(const char* name
, const char* value
)
251 return m_ExtraAttributes
.Put(NPT_String(name
), NPT_String(value
));
254 /*----------------------------------------------------------------------
255 | PLT_StateVariable::Serialize
256 +---------------------------------------------------------------------*/
258 PLT_StateVariable::Serialize(NPT_XmlElementNode
& node
)
260 NPT_List
<NPT_Map
<NPT_String
, NPT_String
>::Entry
*>::Iterator entry
=
261 m_ExtraAttributes
.GetEntries().GetFirstItem();
263 const NPT_String
& key
= (*entry
)->GetKey();
264 const NPT_String
& value
= (*entry
)->GetValue();
265 node
.SetAttribute(key
, value
);
268 return node
.SetAttribute("val", GetValue());