Estou migrando algum código do Qt 6.2.2 para o 6.9.0 no Android.
Tenho um código procurando arquivos .so na pasta do aplicativo (para possíveis plugins a serem carregados). Este código costumava iterar a pasta do aplicativo usando std::filesystem
código padrão. Não funciona mais. Consigo iterar a pasta HOME, mas não a pasta do aplicativo. Surpreendentemente QDir
, consigo, mas meu código que faz isso é puramente C++/STL, não consigo usar Qt neste nível.
Algo mudou na estrutura do apk? Por que o STL não consegue ver a pasta do aplicativo? Existe alguma solução alternativa?
Aqui está um programa de exemplo muito simples:
#include <QApplication>
#include <QMainWindow>
#include <QLabel>
#include <QDebug>
#include <QDir>
#include <filesystem>
void listDirContent(QString path)
{
{
QDir dir(path);
qDebug() << "Using Qt, " << path << ":";
for (auto file : dir.entryList())
qDebug() << file;
}
{
std::filesystem::path std_path = path.toStdString();
qDebug() << "using std, " << std_path.c_str() << ":";
std::filesystem::directory_iterator itDir;
std::filesystem::directory_iterator itEnd;
std::filesystem::path Path;
try
{
itDir = std::filesystem::directory_iterator(std_path);
qDebug() << "Found files:";
for (; itDir != itEnd; itDir++)
{
qDebug() << QString(itDir->path().c_str());
}
qDebug() << "end files";
}
catch (const std::exception& e)
{
qDebug() << "FAILED" << e.what();
}
}
}
int main( int argc, char* argv[] )
{
QApplication app(argc, argv);
QMainWindow wnd;
wnd.setCentralWidget(new QLabel("Hello",&wnd));
wnd.show();
listDirContent(qApp->applicationDirPath());
listDirContent(QDir::homePath());
return app.exec();
}
Este programa produz:
D/default (18701): Using Qt, "/data/app/org.qtproject.example.TestListDir-UzLzgFYV8gnNNAzUQkD1Lw==/base.apk!/lib/armeabi-v7a" :
D/default (18701): "armeabi-v7a"
D/default (18701): "libc++_shared.so"
D/default (18701): "libplugins_iconengines_qsvgicon_armeabi-v7a.so"
D/default (18701): "libplugins_imageformats_qgif_armeabi-v7a.so"
D/default (18701): "libplugins_imageformats_qico_armeabi-v7a.so"
D/default (18701): "libplugins_imageformats_qjpeg_armeabi-v7a.so"
D/default (18701): "libplugins_imageformats_qsvg_armeabi-v7a.so"
D/default (18701): "libplugins_platforms_qtforandroid_armeabi-v7a.so"
D/default (18701): "libplugins_styles_qandroidstyle_armeabi-v7a.so"
D/default (18701): "libQt6Core_armeabi-v7a.so"
D/default (18701): "libQt6Gui_armeabi-v7a.so"
D/default (18701): "libQt6Svg_armeabi-v7a.so"
D/default (18701): "libQt6Widgets_armeabi-v7a.so"
D/default (18701): "libTestListDir_armeabi-v7a.so"
D/default (18701): using std, /data/app/org.qtproject.example.TestListDir-UzLzgFYV8gnNNAzUQkD1Lw==/base.apk!/lib/armeabi-v7a :
D/default (18701): FAILED filesystem error: in directory_iterator::directory_iterator(...): No such file or directory ["/data/app/org.qtproject.example.TestListDir-FvVxa-eHXbBc9Zpa2Q0uGQ==/base.apk!/lib/armeabi-v7a"]
D/default (18701): Using Qt, "/data/user/0/org.qtproject.example.TestListDir/files" :
D/default (18701): "."
D/default (18701): ".."
D/default (18701): "profileInstalled"
D/default (18701): "profileinstaller_profileWrittenFor_lastUpdateTime.dat"
D/default (18701): using std, /data/user/0/org.qtproject.example.TestListDir/files :
D/default (18701): Found files:
D/default (18701): /data/user/0/org.qtproject.example.TestListDir/files/profileinstaller_profileWrittenFor_lastUpdateTime.dat
D/default (18701): /data/user/0/org.qtproject.example.TestListDir/files/profileInstalled
D/default (18701): end files
Veja que std::filesystem não consegue iterar /data/app/org.qtproject.example.TestListDir-UzLzgFYV8gnNNAzUQkD1Lw==/base.apk!/lib/armeabi-v7a
a pasta, ele relata que a pasta não existe, enquanto o Qt consegue iterar por ela.
Com o Qt 6.2.2, ele costumava listar os arquivos da pasta do aplicativo (o que era um pouco diferente, não havia "base.apk!" no caminho).
Relatei um bug no Qt: https://bugreports.qt.io/browse/QTBUG-136214
Alguém tem alguma ideia de como contornar esse problema? Como fazer com que o std::filestem consiga acessar a pasta do aplicativo?
Editar, std::filesystem
é capaz de iterar /data/app/org.qtproject.example.TestListDir-UzLzgFYV8gnNNAzUQkD1Lw==
, visto base.apk
como um arquivo. Parece QDir
suportar um caso especial em que o nome do arquivo apk é seguido por !
e é possível examiná-lo como se fosse, na verdade, uma pasta...