7#include <private/qtqmlglobal_p.h>
9#include <QtCore/qtconfigmacros.h>
10#include <QtCore/qregularexpression.h>
11#include <QtCore/qdirlisting.h>
12#include <QtCore/qfile.h>
14#if QT_CONFIG(qmlcontextpropertydump)
15# include <QtCore/qsettings.h>
19# include <QtCore/qprocess.h>
31 R"x((\.|->)setContextProperty\s*\(\s*(QStringLiteral\s*\(|QString\s*\(|QLatin1String(View)?\s*\(|u)?\s*"([^"]*)")x"_L1;
37 "*.cpp"_L1,
"*.cxx"_L1,
"*.cc"_L1,
"*.c"_L1,
"*.c++"_L1,
38 "*.hpp"_L1,
"*.hxx"_L1,
"*.hh"_L1,
"*.h"_L1,
"*.h++"_L1,
47 const auto it = m_properties.find(name);
48 if (it != m_properties.end())
55 if (
const auto it = m_properties.find(name); it != m_properties.end()) {
56 it.value().append(property);
59 m_properties.insert(name, { property });
65 if (!file.open(QIODevice::ReadOnly | QIODevice::Text))
68 const QString fileContent = QString::fromUtf8(file.readAll());
69 for (
const auto &match : s_matchSetContextProperty.globalMatch(fileContent)) {
70 const quint32 offset = match.capturedStart(s_contextPropertyNameIdxInPattern);
71 const quint32 length = match.capturedLength(s_contextPropertyNameIdxInPattern);
72 const auto [row, column] = QQmlJS::SourceLocation::rowAndColumnFrom(fileContent, offset);
73 const QQmlJS::SourceLocation sourceLocation{ offset, length, row, column };
75 add(match.captured(s_contextPropertyNameIdxInPattern),
76 HeuristicContextProperty{ filePath, sourceLocation });
82 const QStringList fileFilters{ s_fileFilters.begin(), s_fileFilters.end() };
84 for (
const QString &url : rootUrls) {
85 for (
const auto &dirEntry : QDirListing{ url, fileFilters,
86 QDirListing::IteratorFlag::Recursive
87 | QDirListing::IteratorFlag::FilesOnly }) {
89 const QString filePath = dirEntry.filePath();
90 collectFromFile(filePath);
95#if QT_CONFIG(process) && !defined(Q_OS_WINDOWS)
107 result.collectFromDirs(cppSourceDirs);
112
113
114
115
121#if QT_CONFIG(process) && !defined(Q_OS_WINDOWS)
122 if (qEnvironmentVariableIsSet(
"QT_QML_NO_GREP")) {
128 QStringList arguments{
"--recursive"_L1,
130 "--files-with-matches"_L1,
131 "--extended-regexp"_L1,
136 for (
const auto fileFilter : s_fileFilters)
137 arguments <<
"--include"_L1 << fileFilter;
139 arguments.append(dirs);
140 grep.start(
"grep"_L1, arguments);
141 grep.waitForFinished();
142 if (grep.exitStatus() == QProcess::NormalExit) {
143 switch (grep.exitCode()) {
145 const QString output = QString::fromUtf8(grep.readAllStandardOutput());
146 parseGrepOutput(output);
159#if QT_CONFIG(qmlcontextpropertydump)
162 constexpr int size = 4;
172 for (
int i = 0;
i <
size; ++
i) {
198#if QT_CONFIG(qmlcontextpropertydump)
199 HeuristicContextProperties result;
200 std::vector<QString> names;
202 const int size = settings->beginReadArray(cachedHeuristicListKey);
203 for (
int i = 0; i < size; ++i) {
204 settings->setArrayIndex(i);
205 names.push_back(settings->value(
"name").toString());
207 settings->endArray();
209 for (
const auto &name : names) {
210 const int size = settings->beginReadArray(u"property_"_s.append(name));
211 for (
int i = 0; i < size; ++i) {
212 settings->setArrayIndex(i);
215 HeuristicContextProperty{
216 settings->value(
"fileName").toString(),
217 deserializeSourceLocation(settings->value(
"sourceLocation").toString()),
220 settings->endArray();
225 return HeuristicContextProperties{};
231#if QT_CONFIG(qmlcontextpropertydump)
232 QSettings settings(folder +
"/.qt/contextPropertyDump.ini"_L1, QSettings::IniFormat);
233 settings.beginWriteArray(cachedHeuristicListKey);
235 for (
const auto &[name, _] : m_properties) {
236 settings.setArrayIndex(index++);
237 settings.setValue(
"name", name);
241 for (
const auto &[name, definitions] : m_properties) {
242 settings.beginWriteArray(u"property_"_s.append(name));
243 for (
int i = 0; i < definitions.size(); ++i) {
244 settings.setArrayIndex(i);
245 settings.setValue(
"fileName", definitions[i].filename);
246 settings.setValue(
"sourceLocation", serializeSourceLocation(definitions[i].location));
void add(const QString &name, const HeuristicContextProperty &property)
static HeuristicContextProperties collectFrom(QSettings *settings)
void writeCache(const QString &folder) const
QList< HeuristicContextProperty > definitionsForName(const QString &name) const
static const QRegularExpression s_matchSetContextProperty
static constexpr auto cachedHeuristicListKey
static constexpr QLatin1StringView s_pattern
static constexpr int s_contextPropertyNameIdxInPattern
static constexpr std::array s_fileFilters
Combined button and popup list for selecting options.