Update change log and spec for wrt-plugins-tizen_0.4.57
[platform/framework/web/wrt-plugins-tizen.git] / src / Alarm / JSAlarmAbsolute.cpp
1 //
2 // Tizen Web Device API
3 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
4 //
5 // Licensed under the Apache License, Version 2.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 // http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an AS IS BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17
18 #include <CommonsJavaScript/JSUtils.h>
19 #include <CommonsJavaScript/Converter.h>
20 #include <CommonsJavaScript/Validator.h>
21 #include <CommonsJavaScript/JSDOMExceptionFactory.h>
22
23 #include <ArgumentValidator.h>
24
25 #include <Commons/Exception.h>
26 #include <JSWebAPIErrorFactory.h>
27 #include <SecurityExceptions.h>
28
29 #include "AlarmAbsolute.h"
30 #include "AlarmConverter.h"
31 #include <app.h>
32 #include <time.h>
33 #include <JSUtil.h>
34
35 #include <TimeTracer.h>
36 #include "plugin_config.h"
37 #include "JSAlarmAbsolute.h"
38 #include "JSAlarmManager.h"
39 #include <Export.h>
40 #include <Logger.h>
41
42 namespace DeviceAPI {
43 namespace Alarm {
44
45 using namespace WrtDeviceApis::Commons;
46 using namespace WrtDeviceApis::CommonsJavaScript;
47 using namespace DeviceAPI::Common;
48
49 JSClassRef JSAlarmAbsolute::m_jsClassRef = NULL;
50
51 JSClassDefinition JSAlarmAbsolute::m_jsClassInfo = {
52         0,
53         kJSClassAttributeNone,
54         TIZEN_ALARM_ABSOLUTE_INTERFACE,
55         NULL,
56         m_property,
57         m_function,
58         initialize,
59         finalize,
60         NULL, //hasProperty,
61         NULL, //getProperty,
62         NULL, //setProperty,
63         NULL, //deleteProperty,Geolocation
64         NULL, //getPropertyNames,
65         NULL,
66         NULL, // constructor
67         NULL,
68         NULL
69 };
70
71 JSStaticFunction JSAlarmAbsolute::m_function[] = { 
72     { ALARM_FUNCTION_API_GET_NEXT_SCHEDULED_DATE, JSAlarmAbsolute::getNextScheduledDate, kJSPropertyAttributeNone },
73     { 0, 0, 0 }
74 };
75
76 JSStaticValue JSAlarmAbsolute::m_property[] = {
77     { TIZEN_ALARM_ABSOLUTE_ATTRIBUTE_ID, getId, NULL, kJSPropertyAttributeReadOnly },
78     { TIZEN_ALARM_ABSOLUTE_ATTRIBUTE_DATE, getDate, NULL, kJSPropertyAttributeReadOnly },
79     { TIZEN_ALARM_ABSOLUTE_ATTRIBUTE_PERIOD, getInterval, NULL, kJSPropertyAttributeReadOnly },
80     { TIZEN_ALARM_ABSOLUTE_ATTRIBUTE_DAYSOFTHEWEEK, getDaysOfTheWeek, NULL, kJSPropertyAttributeReadOnly },
81     { 0, 0, 0, 0 }                                                                                            
82 };
83
84 const JSClassRef DLL_EXPORT JSAlarmAbsolute::getClassRef()
85 {
86     if (!m_jsClassRef) {
87         m_jsClassRef = JSClassCreate(&m_jsClassInfo);
88     }
89     return m_jsClassRef;
90 }
91
92 const JSClassDefinition* JSAlarmAbsolute::getClassInfo() 
93 {
94     return &m_jsClassInfo;
95 }
96
97 void JSAlarmAbsolute::initialize(JSContextRef context, JSObjectRef object) 
98 {
99 }
100 void JSAlarmAbsolute::finalize(JSObjectRef object) 
101 {
102     JSAlarmAbsolutePriv *priv = static_cast<JSAlarmAbsolutePriv*>(JSObjectGetPrivate(object));
103     if (!priv) {
104         LoggerE("Private object is null");
105     }
106     delete priv;
107
108 }
109
110
111 JSObjectRef DLL_EXPORT JSAlarmAbsolute::constructor(JSContextRef ctx, JSObjectRef constructor, size_t argumentCount, const JSValueRef arguments[], JSValueRef* exception)
112 {
113         ArgumentValidator validator(ctx, argumentCount, arguments);
114
115         AlarmAbsolutePtr priv = AlarmAbsolutePtr(new AlarmAbsolute());
116
117     try {
118         time_t date = validator.toTimeT(0);
119         struct tm *startDate = localtime(&date);
120         mktime(startDate);
121         
122         priv->setDate(*startDate);
123
124         if (argumentCount >= 2) {
125             if (JSIsArrayValue(ctx, arguments[1])) {
126                 std::vector<std::string> daysOfTheWeek =  validator.toStringVector(1);
127
128                 for (int i = 0; i < daysOfTheWeek.size(); i++ ) {
129                     if ( (daysOfTheWeek[i]!="SU") && (daysOfTheWeek[i]!="MO") &&
130                          (daysOfTheWeek[i]!="TU") && (daysOfTheWeek[i]!="WE") &&
131                          (daysOfTheWeek[i]!="TH") && (daysOfTheWeek[i]!="FR") &&
132                          (daysOfTheWeek[i]!="SA") ) {
133                         // remove unacceptable data from vector
134                         daysOfTheWeek.erase(std::remove(daysOfTheWeek.begin(), daysOfTheWeek.end(), daysOfTheWeek[i]), daysOfTheWeek.end());
135                     }
136                 }
137
138                 if(daysOfTheWeek.size() > 0) {
139                     priv->setByDayRecurrence(daysOfTheWeek);    
140                 }
141             } else {
142                 long interval = validator.toLong(1);
143                 if (interval < 0) {
144                     throw InvalidValuesException("period can not be negative value");
145                 }
146
147                 priv->setInterval(interval);
148             }
149         }
150         } catch (const BasePlatformException& err) {
151                 LoggerE("Exception occured while creating constructor : " << err.getMessage());
152         }
153
154         JSAlarmAbsolutePriv *jspriv = new JSAlarmAbsolutePriv(ctx, priv);
155         JSObjectRef obj = JSObjectMake(ctx, getClassRef(), jspriv);
156
157     JSStringRef ctorName = JSStringCreateWithUTF8CString("constructor");
158     JSObjectSetProperty(ctx, obj, ctorName, constructor,
159         kJSPropertyAttributeReadOnly | kJSPropertyAttributeDontDelete | kJSPropertyAttributeDontEnum, NULL);
160     JSStringRelease(ctorName);
161
162         return obj;
163 }
164
165 AlarmAbsolutePtr JSAlarmAbsolute::getPrivData(JSObjectRef object)
166 {
167     JSAlarmAbsolutePriv *priv = static_cast<JSAlarmAbsolutePriv*>(JSObjectGetPrivate(object));
168     if (!priv) {
169         throw TypeMismatchException("Private object is null");
170     }
171     AlarmAbsolutePtr result = priv->getObject();
172     if (!result) {
173         throw TypeMismatchException("Private object is null");
174     }
175     return result;
176 }
177
178
179 JSValueRef JSAlarmAbsolute::createJSObject(JSContextRef context, AlarmAbsolutePtr privateData)
180 {
181     JSAlarmAbsolutePriv *priv = new JSAlarmAbsolutePriv(context, privateData);
182     if (!priv) {
183         throw TypeMismatchException("Private object is null");
184     }
185     return JSObjectMake(context, getClassRef(), static_cast<void*>(priv));
186 }
187
188 JSValueRef JSAlarmAbsolute::getNextScheduledDate( JSContextRef ctx, JSObjectRef function, JSObjectRef thisObject, size_t argumentCount, const JSValueRef arguments[], JSValueRef * exception)
189 {   
190     TIME_TRACER_ITEM_BEGIN(__FUNCTION__, 0);
191     try {
192         struct tm date;
193         Converter converter(ctx);
194         
195         AlarmAbsolutePtr privateData = getPrivData(thisObject);
196         if (!privateData) {
197             throw TypeMismatchException("Private object is null");
198         }
199         
200         if(!privateData->is_registered) {
201             return JSValueMakeNull(ctx);
202         }
203
204         int id = privateData->getId();
205         TIME_TRACER_ITEM_BEGIN("(getNextScheduledDate)alarm_get_scheduled_date", 0);
206         int err = alarm_get_scheduled_date(id, &date);
207         TIME_TRACER_ITEM_END("(getNextScheduledDate)alarm_get_scheduled_date", 0);
208         if(err != ALARM_ERROR_NONE) {
209             return JSValueMakeNull(ctx);
210         }
211
212         // check wheter the alarm is expired or not
213         struct tm curr_date;
214         TIME_TRACER_ITEM_BEGIN("(getNextScheduledDate)alarm_get_current_time", 0);
215         err = alarm_get_current_time(&curr_date);
216         TIME_TRACER_ITEM_END("(getNextScheduledDate)alarm_get_current_time", 0);
217         if(err != ALARM_ERROR_NONE) {
218             return JSValueMakeNull(ctx);
219         }
220
221         if (mktime(&date) < mktime(&curr_date)) {
222             return JSValueMakeNull(ctx);
223         }
224         TIME_TRACER_ITEM_END(__FUNCTION__, 0);
225
226         return converter.toJSValueRef(date);
227         
228     } catch (const BasePlatformException &err) {
229         return JSWebAPIErrorFactory::postException(ctx, exception, err);
230     } catch (...) {
231         DeviceAPI::Common::UnknownException err("Unknown Error in ApplicationManager.getAppSharedURI().");
232         return JSWebAPIErrorFactory::postException(ctx, exception, err);
233     }
234 }
235
236 JSValueRef JSAlarmAbsolute::getDate(JSContextRef ctx,
237         JSObjectRef object,
238         JSStringRef propertyName,
239         JSValueRef* exception)
240 {
241     Converter converter(ctx);
242     struct tm date;
243
244     try {
245         AlarmAbsolutePtr privateData = getPrivData(object);
246         if (!privateData) {
247             throw TypeMismatchException("Private object is null");
248         }
249         
250         date = privateData->getDate();
251         LoggerI("JSAlarmAbsolute Date  = " << "  Sec : " << date.tm_sec << "  Min : "<< date.tm_min
252         << "  Hour" << date.tm_hour << "Day : " << date.tm_mday << "  MON : " << date.tm_mon 
253         << "  Year : " <<  date.tm_year);
254
255         JSValueRef args[6];
256         args[0] = JSValueMakeNumber(ctx, date.tm_year + 1900);
257         args[1] = JSValueMakeNumber(ctx, date.tm_mon);
258         args[2] = JSValueMakeNumber(ctx, date.tm_mday);
259         args[3] = JSValueMakeNumber(ctx, date.tm_hour);
260         args[4] = JSValueMakeNumber(ctx, date.tm_min);
261         args[5] = JSValueMakeNumber(ctx, date.tm_sec);
262
263         JSObjectRef result = JSObjectMakeDate(ctx, 6, args, exception);
264         return result;
265     } catch (...) {
266         LoggerE("Exception: occured");
267     }
268
269     return JSValueMakeUndefined(ctx);
270 }
271
272 JSValueRef JSAlarmAbsolute::getId(JSContextRef ctx,
273         JSObjectRef object,
274         JSStringRef propertyName,
275         JSValueRef* exception)
276 {
277     try {
278         AlarmAbsolutePtr privateData = getPrivData(object);
279         if (!privateData) {
280             throw TypeMismatchException("Private object is null");
281         }
282         
283         Converter converter(ctx);
284         if (privateData->is_registered) {
285             std::string strId = converter.toString(privateData->getId());
286             return converter.toJSValueRef(strId);
287         } else {
288             return JSValueMakeNull(ctx);
289         }
290     } catch (...) {
291         LoggerE("Exception: occured");
292     }
293
294     return JSValueMakeUndefined(ctx);
295 }
296
297 JSValueRef JSAlarmAbsolute::getInterval(JSContextRef ctx,
298         JSObjectRef object,
299         JSStringRef propertyName,
300         JSValueRef* exception)
301 {
302     try {
303         AlarmAbsolutePtr privateData = getPrivData(object);
304         AbsoluteRecurrence::Type alarmType = privateData->getRecurrenceType();
305        
306         if(alarmType == AbsoluteRecurrence::Interval) {
307             long interval = privateData->getInterval();
308             if (interval == -1 ) {
309                 return JSValueMakeNull(ctx);
310             } else {
311                 return DeviceAPI::Common::JSUtil::toJSValueRef(ctx, interval);
312             }
313         } else {
314             return JSValueMakeNull(ctx);    
315         }
316     } catch (...) {
317         LoggerI("Exception: occured");
318     }
319
320     return JSValueMakeUndefined(ctx);
321 }
322
323 JSValueRef JSAlarmAbsolute::getDaysOfTheWeek(JSContextRef ctx,
324         JSObjectRef object,
325         JSStringRef propertyName,
326         JSValueRef* exception)
327 {
328     Converter converter(ctx);
329     
330     try {
331         AlarmAbsolutePtr privateData = getPrivData(object);
332         if (!privateData) {
333             throw TypeMismatchException("Private object is null");
334         }
335
336         JSObjectRef jsResult = JSCreateArrayObject(ctx, 0, NULL);
337         if (jsResult == NULL) {
338             throw UnknownException("Could not create js array object");
339         }
340         
341         std::vector<std::string> daysOfTheWeek = privateData->getByDayRecurrence();
342
343         if(daysOfTheWeek.size() > 0) {
344             for(size_t i = 0; i<daysOfTheWeek.size(); i++) {
345                 JSValueRef val = converter.toJSValueRef(daysOfTheWeek.at(i));
346                 if(!JSSetArrayElement(ctx, jsResult, i, val)) {
347                     throw UnknownException("Could not insert value into js array");
348                 }
349             }
350         }
351
352         return jsResult;
353     } catch (...) {
354         LoggerI("Exception: occured");
355     }
356
357     return JSValueMakeUndefined(ctx);
358 }
359
360 } // Alarm
361 } // TizenApis
362
363