Qt 4.8
qdeclarativeinclude.cpp
Go to the documentation of this file.
1 /****************************************************************************
2 **
3 ** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/legal
5 **
6 ** This file is part of the QtDeclarative module of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and Digia. For licensing terms and
14 ** conditions see http://qt.digia.com/licensing. For further information
15 ** use the contact form at http://qt.digia.com/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 as published by the Free Software
20 ** Foundation and appearing in the file LICENSE.LGPL included in the
21 ** packaging of this file. Please review the following information to
22 ** ensure the GNU Lesser General Public License version 2.1 requirements
23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24 **
25 ** In addition, as a special exception, Digia gives you certain additional
26 ** rights. These rights are described in the Digia Qt LGPL Exception
27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28 **
29 ** GNU General Public License Usage
30 ** Alternatively, this file may be used under the terms of the GNU
31 ** General Public License version 3.0 as published by the Free Software
32 ** Foundation and appearing in the file LICENSE.GPL included in the
33 ** packaging of this file. Please review the following information to
34 ** ensure the GNU General Public License version 3.0 requirements will be
35 ** met: http://www.gnu.org/copyleft/gpl.html.
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41 
42 #include "qdeclarativeinclude_p.h"
43 
44 #include <QtScript/qscriptengine.h>
45 #include <QtNetwork/qnetworkrequest.h>
46 #include <QtNetwork/qnetworkreply.h>
47 #include <QtCore/qfile.h>
48 
49 #include <private/qdeclarativeengine_p.h>
50 #include <private/qdeclarativeglobalscriptclass_p.h>
51 
53 
55  QDeclarativeEngine *engine,
56  QScriptContext *ctxt)
57 : QObject(engine), m_engine(engine), m_network(0), m_reply(0), m_url(url), m_redirectCount(0)
58 {
61 
64 
67 
69 
70  QNetworkRequest request;
71  request.setUrl(url);
72 
73  m_reply = m_network->get(request);
75 }
76 
78 {
79  delete m_reply;
80 }
81 
83 {
84  QScriptValue result = engine->newObject();
85  result.setProperty(QLatin1String("OK"), QScriptValue(engine, Ok));
86  result.setProperty(QLatin1String("LOADING"), QScriptValue(engine, Loading));
87  result.setProperty(QLatin1String("NETWORK_ERROR"), QScriptValue(engine, NetworkError));
88  result.setProperty(QLatin1String("EXCEPTION"), QScriptValue(engine, Exception));
89 
90  result.setProperty(QLatin1String("status"), QScriptValue(engine, status));
91  return result;
92 }
93 
95 {
96  return m_result;
97 }
98 
100 {
101  m_callback = c;
102 }
103 
105 {
106  return m_callback;
107 }
108 
109 #define INCLUDE_MAXIMUM_REDIRECT_RECURSION 15
111 {
112  m_redirectCount++;
113 
116  if (redirect.isValid()) {
117  m_url = m_url.resolved(redirect.toUrl());
118  delete m_reply;
119 
120  QNetworkRequest request;
121  request.setUrl(m_url);
122 
123  m_reply = m_network->get(request);
125  return;
126  }
127  }
128 
131 
133 
134  QString code = QString::fromUtf8(data);
135 
136  QString urlString = m_url.toString();
138  scriptContext->pushScope(ep->contextClass->newUrlContext(m_context, 0, urlString));
139  scriptContext->pushScope(m_scope[0]);
140 
141  scriptContext->pushScope(m_scope[1]);
142  scriptContext->setActivationObject(m_scope[1]);
144 
145  m_scriptEngine->evaluate(code, urlString, 1);
146 
148 
153  } else {
155  }
156  } else {
158  }
159 
161 
162  disconnect();
163  deleteLater();
164 }
165 
167 {
168  if (callback.isValid()) {
169  QScriptValue args = engine->newArray(1);
170  args.setProperty(0, status);
171  callback.call(QScriptValue(), args);
172  }
173 }
174 
175 /*
176  Documented in qdeclarativeengine.cpp
177 */
179 {
180  if (ctxt->argumentCount() == 0)
181  return engine->undefinedValue();
182 
184 
186  if (contextUrl.isEmpty())
187  return ctxt->throwError(QLatin1String("Qt.include(): Can only be called from JavaScript files"));
188 
189  QString urlString = ctxt->argument(0).toString();
190  QUrl url(urlString);
191  if (url.isRelative()) {
192  url = QUrl(contextUrl).resolved(url);
193  urlString = url.toString();
194  }
195 
197 
198  QScriptValue func = ctxt->argument(1);
199  if (!func.isFunction())
200  func = QScriptValue();
201 
203  if (localFile.isEmpty()) {
204  QDeclarativeInclude *i =
206 
207  if (func.isValid())
208  i->setCallback(func);
209 
210  result = i->result();
211  } else {
212 
213  QFile f(localFile);
214  if (f.open(QIODevice::ReadOnly)) {
215  QByteArray data = f.readAll();
216  QString code = QString::fromUtf8(data);
217 
218  QDeclarativeContextData *context =
220 
222  scriptContext->pushScope(ep->contextClass->newUrlContext(context, 0, urlString));
223  scriptContext->pushScope(ep->globalClass->staticGlobalObject());
225  scriptContext->pushScope(scope);
226  scriptContext->setActivationObject(scope);
228 
229  engine->evaluate(code, urlString, 1);
230 
231  engine->popContext();
232 
233  if (engine->hasUncaughtException()) {
234  result = resultValue(engine, Exception);
235  result.setProperty(QLatin1String("exception"), engine->uncaughtException());
236  engine->clearExceptions();
237  } else {
238  result = resultValue(engine, Ok);
239  }
240  callback(engine, func, result);
241  } else {
242  result = resultValue(engine, NetworkError);
243  callback(engine, func, result);
244  }
245  }
246 
247  return result;
248 }
249 
251 {
252  if (ctxt->argumentCount() == 0)
253  return engine->undefinedValue();
254 
255  QString urlString = ctxt->argument(0).toString();
256  QUrl url(ctxt->argument(0).toString());
257  if (url.isRelative()) {
259  Q_ASSERT(!contextUrl.isEmpty());
260 
261  url = QUrl(contextUrl).resolved(url);
262  urlString = url.toString();
263  }
264 
266 
267  QScriptValue func = ctxt->argument(1);
268  if (!func.isFunction())
269  func = QScriptValue();
270 
272  if (!localFile.isEmpty()) {
273 
274  QFile f(localFile);
275  if (f.open(QIODevice::ReadOnly)) {
276  QByteArray data = f.readAll();
277  QString code = QString::fromUtf8(data);
278 
280  QScriptValue urlContext = engine->newObject();
281  urlContext.setData(QScriptValue(engine, urlString));
282  scriptContext->pushScope(urlContext);
283 
285  scriptContext->pushScope(scope);
286  scriptContext->setActivationObject(scope);
288 
289  engine->evaluate(code, urlString, 1);
290 
291  engine->popContext();
292 
293  if (engine->hasUncaughtException()) {
294  result = resultValue(engine, Exception);
295  result.setProperty(QLatin1String("exception"), engine->uncaughtException());
296  engine->clearExceptions();
297  } else {
298  result = resultValue(engine, Ok);
299  }
300  callback(engine, func, result);
301  } else {
302  result = resultValue(engine, NetworkError);
303  callback(engine, func, result);
304  }
305  }
306 
307  return result;
308 }
309 
The QVariant class acts like a union for the most common Qt data types.
Definition: qvariant.h:92
static QString urlToLocalFileOrQrc(const QUrl &url)
static QScriptEngine * getScriptEngine(QDeclarativeEngine *e)
The QScriptContext class represents a Qt Script function invocation.
QScriptValue newUrlContext(QDeclarativeContextData *, QObject *, const QString &)
void setUrl(const QUrl &url)
Sets the URL this network request is referring to to be url.
NetworkError error() const
Returns the error that was found during the processing of this request.
QScriptValue evaluate(const QString &program, const QString &fileName=QString(), int lineNumber=1)
Evaluates program, using lineNumber as the base line number, and returns the result of the evaluation...
virtual QNetworkAccessManager * networkAccessManager()
unsigned char c[8]
Definition: qnumeric_p.h:62
#define QT_END_NAMESPACE
This macro expands to.
Definition: qglobal.h:90
bool isFunction() const
Returns true if this QScriptValue is a function; otherwise returns false.
QString toString(FormattingOptions options=None) const
Returns the human-displayable string representation of the URL.
Definition: qurl.cpp:5896
bool open(OpenMode flags)
Opens the file using OpenMode mode, returning true if successful; otherwise false.
Definition: qfile.cpp:1064
QVariant attribute(QNetworkRequest::Attribute code) const
Returns the attribute associated with the code code.
static QScriptValue include(QScriptContext *ctxt, QScriptEngine *engine)
static QDeclarativeEngine * getEngine(QScriptEngine *e)
The QByteArray class provides an array of bytes.
Definition: qbytearray.h:135
QScriptValue throwError(Error error, const QString &text)
Throws an error with the given text.
bool isEmpty() const
Returns true if the URL has no data; otherwise returns false.
Definition: qurl.cpp:4317
#define SLOT(a)
Definition: qobjectdefs.h:226
QString toString() const
Returns the string value of this QScriptValue, as defined in ECMA-262 section 9.8, "ToString".
QDeclarativeGlobalScriptClass * globalClass
QDeclarativeGuard< QNetworkReply > m_reply
static LibLoadStatus status
Definition: qlocale_icu.cpp:69
QLatin1String(DBUS_INTERFACE_DBUS))) Q_GLOBAL_STATIC_WITH_ARGS(QString
static QScriptValue worker_include(QScriptContext *ctxt, QScriptEngine *engine)
void popContext()
Pops the current execution context and restores the previous one.
QDeclarativeContextData * contextFromValue(const QScriptValue &)
The QUrl class provides a convenient interface for working with URLs.
Definition: qurl.h:61
The QString class provides a Unicode character string.
Definition: qstring.h:83
#define Q_ASSERT(cond)
Definition: qglobal.h:1823
The QObject class is the base class of all Qt objects.
Definition: qobject.h:111
static QDeclarativeEnginePrivate * get(QDeclarativeEngine *e)
static QDeclarativeParser::Object::ScriptBlock::Pragmas extractPragmas(QString &)
bool isRelative() const
Returns true if the URL is relative; otherwise returns false.
Definition: qurl.cpp:5880
static QDeclarativeScriptEngine * get(QScriptEngine *e)
void setActivationObject(const QScriptValue &activation)
Sets the activation object of this QScriptContext to be the given activation.
const QScriptValue & staticGlobalObject() const
#define SIGNAL(a)
Definition: qobjectdefs.h:227
The QScriptEngine class provides an environment for evaluating Qt Script code.
#define QT_BEGIN_NAMESPACE
This macro expands to.
Definition: qglobal.h:89
void setCallback(const QScriptValue &)
static bool connect(const QObject *sender, const char *signal, const QObject *receiver, const char *member, Qt::ConnectionType=Qt::AutoConnection)
Creates a connection of the given type from the signal in the sender object to the method in the rece...
Definition: qobject.cpp:2580
bool isEmpty() const
Returns true if the string has no characters; otherwise returns false.
Definition: qstring.h:704
QDeclarativeGuardedContextData m_context
static QString fromUtf8(const char *, int size=-1)
Returns a QString initialized with the first size bytes of the UTF-8 string str.
Definition: qstring.cpp:4302
QDeclarativeEngine * m_engine
static const char * data(const QByteArray &arr)
The QLatin1String class provides a thin wrapper around an US-ASCII/Latin-1 encoded string literal...
Definition: qstring.h:654
QScriptValue newObject()
Creates a QtScript object of class Object.
QScriptValue result() const
QNetworkReply * get(const QNetworkRequest &request)
Posts a request to obtain the contents of the target request and returns a new QNetworkReply object o...
QUrl toUrl() const
Returns the variant as a QUrl if the variant has type() Url ; otherwise returns an invalid QUrl...
Definition: qvariant.cpp:2528
int argumentCount() const
Returns the number of arguments passed to the function in this invocation.
static QScriptValue resultValue(QScriptEngine *, Status status=Loading)
QScriptValue callback() const
static bool disconnect(const QObject *sender, const char *signal, const QObject *receiver, const char *member)
Disconnects signal in object sender from method in object receiver.
Definition: qobject.cpp:2895
QScriptValue data() const
Returns the internal data of this QScriptValue object.
void setProperty(const QString &name, const QScriptValue &value, const PropertyFlags &flags=KeepExistingFlags)
Sets the value of this QScriptValue&#39;s property with the given name to the given value.
The QFile class provides an interface for reading from and writing to files.
Definition: qfile.h:65
The QDeclarativeEngine class provides an environment for instantiating QML components.
QScriptEngine * m_scriptEngine
QDeclarativeInclude(const QUrl &, QDeclarativeEngine *, QScriptContext *ctxt)
static QScriptValue scopeChainValue(QScriptContext *, int index)
#define INCLUDE_MAXIMUM_REDIRECT_RECURSION
QByteArray readAll()
Reads all available data from the device, and returns it as a QByteArray.
Definition: qiodevice.cpp:1025
void clearExceptions()
Clears any uncaught exceptions in this engine.
The QNetworkRequest class holds a request to be sent with QNetworkAccessManager.
QScriptValue undefinedValue()
Returns a QScriptValue of the primitive type Undefined.
QScriptValue newArray(uint length=0)
Creates a QtScript object of class Array with the given length.
QUrl resolved(const QUrl &relative) const
Returns the result of the merge of this URL with relative.
Definition: qurl.cpp:5819
bool isValid() const
Returns true if the storage type of this variant is not QVariant::Invalid; otherwise returns false...
Definition: qvariant.h:485
void pushScope(const QScriptValue &object)
Adds the given object to the front of this context&#39;s scope chain.
bool hasUncaughtException() const
Returns true if the last script evaluation resulted in an uncaught exception; otherwise returns false...
The QScriptValue class acts as a container for the Qt Script data types.
Definition: qscriptvalue.h:57
QScriptValue call(const QScriptValue &thisObject=QScriptValue(), const QScriptValueList &args=QScriptValueList())
Calls this QScriptValue as a function, using thisObject as the `this&#39; object in the function call...
void deleteLater()
Schedules this object for deletion.
Definition: qobject.cpp:2145
QScriptValue argument(int index) const
Returns the function argument at the given index.
bool isValid() const
Returns true if this QScriptValue is valid; otherwise returns false.
static QScriptContext * pushCleanContext(QScriptEngine *)
Enters a new execution context and returns the associated QScriptContext object.
QScriptValue uncaughtException() const
Returns the current uncaught exception, or an invalid QScriptValue if there is no uncaught exception...
void setData(const QScriptValue &data)
Sets the internal data of this QScriptValue object.
QNetworkAccessManager * m_network
QDeclarativeContextScriptClass * contextClass