reformat in uvosstyle

This commit is contained in:
2023-11-02 21:40:24 +01:00
parent c73f72f8c2
commit fc0ca71b4d
4 changed files with 225 additions and 225 deletions

View File

@ -26,218 +26,219 @@
K_PLUGIN_FACTORY_WITH_JSON(KateAiPluginFactory, "kateai.json", registerPlugin<KateAiPlugin>();) K_PLUGIN_FACTORY_WITH_JSON(KateAiPluginFactory, "kateai.json", registerPlugin<KateAiPlugin>();)
KateAiPlugin::KateAiPlugin(QObject *parent, const QList<QVariant> &) KateAiPlugin::KateAiPlugin(QObject *parent, const QList<QVariant> &)
: KTextEditor::Plugin(parent), m_serverUrl(QStringLiteral("ws://localhost:8642")) : KTextEditor::Plugin(parent), m_serverUrl(QStringLiteral("ws://localhost:8642"))
{ {
connect(&m_webSocket, &QWebSocket::connected, this, &KateAiPlugin::onConnected); connect(&m_webSocket, &QWebSocket::connected, this, &KateAiPlugin::onConnected);
readConfig(); readConfig();
} }
void KateAiPlugin::onConnected() void KateAiPlugin::onConnected()
{ {
qDebug()<<__func__<<m_webSocket.isValid(); qDebug()<<__func__<<m_webSocket.isValid();
} }
KateAiPlugin::~KateAiPlugin() = default; KateAiPlugin::~KateAiPlugin() = default;
void KateAiPlugin::reconnect() void KateAiPlugin::reconnect()
{ {
m_webSocket.close(); m_webSocket.close();
m_webSocket.open(m_serverUrl); m_webSocket.open(m_serverUrl);
} }
QObject *KateAiPlugin::createView(KTextEditor::MainWindow *mainWindow) QObject *KateAiPlugin::createView(KTextEditor::MainWindow *mainWindow)
{ {
auto view = new KateAiPluginView(this, mainWindow, &m_webSocket); auto view = new KateAiPluginView(this, mainWindow, &m_webSocket);
connect(view, &KateAiPluginView::reconnect, this, &KateAiPlugin::reconnect); connect(view, &KateAiPluginView::reconnect, this, &KateAiPlugin::reconnect);
return view; return view;
} }
KTextEditor::ConfigPage *KateAiPlugin::configPage(int number, QWidget *parent) KTextEditor::ConfigPage *KateAiPlugin::configPage(int number, QWidget *parent)
{ {
if (number != 0) if (number != 0)
return nullptr; return nullptr;
return new KateAiConfigPage(parent, this); return new KateAiConfigPage(parent, this);
} }
void KateAiPlugin::readConfig() void KateAiPlugin::readConfig()
{ {
KConfigGroup config(KSharedConfig::openConfig(), "Ai"); KConfigGroup config(KSharedConfig::openConfig(), "Ai");
m_serverUrl = QUrl(config.readEntry("Url", "ws://localhost:8642")); m_serverUrl = QUrl(config.readEntry("Url", "ws://localhost:8642"));
reconnect(); reconnect();
} }
KateAiPluginView::KateAiPluginView(KateAiPlugin *plugin, KTextEditor::MainWindow *mainwindow, QPointer<QWebSocket> webSocket, bool instruct) KateAiPluginView::KateAiPluginView(KateAiPlugin *plugin, KTextEditor::MainWindow *mainwindow,
: QObject(plugin) QPointer<QWebSocket> webSocket, bool instruct)
, m_mainWindow(mainwindow) : QObject(plugin)
, m_webSocket(webSocket) , m_mainWindow(mainwindow)
, m_useInstruct(instruct) , m_webSocket(webSocket)
, m_useInstruct(instruct)
{ {
KXMLGUIClient::setComponentName(QStringLiteral("kateaiplugin"), QStringLiteral("Git Blame")); KXMLGUIClient::setComponentName(QStringLiteral("kateaiplugin"), QStringLiteral("Git Blame"));
setXMLFile(QStringLiteral("ui.rc")); setXMLFile(QStringLiteral("ui.rc"));
QAction *generateAction = actionCollection()->addAction(QStringLiteral("ai_generate")); QAction *generateAction = actionCollection()->addAction(QStringLiteral("ai_generate"));
generateAction->setText(QStringLiteral("Generate text using AI")); generateAction->setText(QStringLiteral("Generate text using AI"));
actionCollection()->setDefaultShortcut(generateAction, QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_A)); actionCollection()->setDefaultShortcut(generateAction, QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_A));
m_mainWindow->guiFactory()->addClient(this); m_mainWindow->guiFactory()->addClient(this);
connect(generateAction, &QAction::triggered, this, &KateAiPluginView::generate); connect(generateAction, &QAction::triggered, this, &KateAiPluginView::generate);
connect(m_webSocket, &QWebSocket::textMessageReceived, this, &KateAiPluginView::socketMessage); connect(m_webSocket, &QWebSocket::textMessageReceived, this, &KateAiPluginView::socketMessage);
} }
QPointer<KTextEditor::Document> KateAiPluginView::activeDocument() const QPointer<KTextEditor::Document> KateAiPluginView::activeDocument() const
{ {
KTextEditor::View *view = m_mainWindow->activeView(); KTextEditor::View *view = m_mainWindow->activeView();
if(view && view->document()) if(view && view->document())
return view->document(); return view->document();
return nullptr; return nullptr;
} }
KTextEditor::Cursor KateAiPluginView::getCurrentCursor() const KTextEditor::Cursor KateAiPluginView::getCurrentCursor() const
{ {
KTextEditor::View *view = m_mainWindow->activeView(); KTextEditor::View *view = m_mainWindow->activeView();
if(view) if(view)
return view->cursorPosition(); return view->cursorPosition();
return KTextEditor::Cursor(); return KTextEditor::Cursor();
} }
void KateAiPluginView::socketMessage(const QString& message) void KateAiPluginView::socketMessage(const QString& message)
{ {
QJsonDocument jsonDocument = QJsonDocument::fromJson(message.toUtf8()); QJsonDocument jsonDocument = QJsonDocument::fromJson(message.toUtf8());
QJsonValue idVal = jsonDocument[QStringLiteral("request_id")]; QJsonValue idVal = jsonDocument[QStringLiteral("request_id")];
if(!idVal.isDouble()) if(!idVal.isDouble())
{ {
qDebug()<<"Got invalid response on socket"; qDebug()<<"Got invalid response on socket";
return; return;
} }
int id = idVal.toInt(); int id = idVal.toInt();
QHash<int, Request>::iterator it = m_requests.find(id); QHash<int, Request>::iterator it = m_requests.find(id);
if(it != m_requests.end()) if(it != m_requests.end())
{ {
QJsonValue responseValue = jsonDocument[QStringLiteral("response")]; QJsonValue responseValue = jsonDocument[QStringLiteral("response")];
if(!responseValue.isString()) if(!responseValue.isString())
{ {
qDebug()<<"Got invalid response on socket"; qDebug()<<"Got invalid response on socket";
return; return;
} }
if(it.value().document) if(it.value().document)
it.value().document->insertText(it.value().cursor, responseValue.toString()); it.value().document->insertText(it.value().cursor, responseValue.toString());
m_requests.erase(it); m_requests.erase(it);
} }
} }
QStringList KateAiPluginView::getIncludePaths(const QString& text) QStringList KateAiPluginView::getIncludePaths(const QString& text)
{ {
QStringList lines = text.split(U'\n'); QStringList lines = text.split(U'\n');
QStringList paths; QStringList paths;
for(const QString& line : lines) for(const QString& line : lines)
{ {
if(line.trimmed().startsWith(QStringLiteral("#include"))) if(line.trimmed().startsWith(QStringLiteral("#include")))
{ {
int start = line.indexOf(U'<'); int start = line.indexOf(U'<');
int end; int end;
if(start != -1) if(start != -1)
{ {
end = line.indexOf(U'>', start+1); end = line.indexOf(U'>', start+1);
if(end == -1) if(end == -1)
continue; continue;
} }
else else
{ {
start = line.indexOf(U'"'); start = line.indexOf(U'"');
if(start == -1) if(start == -1)
continue; continue;
end = line.indexOf(U'"', start+1); end = line.indexOf(U'"', start+1);
if(end == -1) if(end == -1)
continue; continue;
} }
paths.push_back(line.mid(start+1, (end-(start+1))).trimmed()); paths.push_back(line.mid(start+1, (end-(start+1))).trimmed());
} }
} }
return paths; return paths;
} }
QString KateAiPluginView::assembleContext(QPointer<KTextEditor::Document> document, const KTextEditor::Cursor& cursor) QString KateAiPluginView::assembleContext(QPointer<KTextEditor::Document> document, const KTextEditor::Cursor& cursor)
{ {
QString mime = document->mimeType(); QString mime = document->mimeType();
QString context; QString context;
QString baseText; QString baseText;
if(!m_useInstruct) if(!m_useInstruct)
baseText = document->text(KTextEditor::Range(KTextEditor::Cursor(0, 0), cursor)); baseText = document->text(KTextEditor::Range(KTextEditor::Cursor(0, 0), cursor));
else else
baseText = document->text(); baseText = document->text();
if(mime == QStringLiteral("text/x-c++src") || mime == QStringLiteral("text/x-csrc")) if(mime == QStringLiteral("text/x-c++src") || mime == QStringLiteral("text/x-csrc"))
{ {
QFileInfo documentFileInfo(document->url().path()); QFileInfo documentFileInfo(document->url().path());
QString directory = documentFileInfo.absolutePath(); QString directory = documentFileInfo.absolutePath();
QStringList paths = getIncludePaths(baseText); QStringList paths = getIncludePaths(baseText);
qDebug()<<__func__<<"Directory:"<<directory<<"Paths:"<<paths; qDebug()<<__func__<<"Directory:"<<directory<<"Paths:"<<paths;
for(QString& path : paths) for(QString& path : paths)
{ {
path = directory + QDir::separator() + path; path = directory + QDir::separator() + path;
qDebug()<<path; qDebug()<<path;
QFile file(path); QFile file(path);
if(!file.isOpen()) if(!file.isOpen())
continue; continue;
QByteArray fileData = file.readAll(); QByteArray fileData = file.readAll();
QString fileText = QString::fromUtf8(fileData); QString fileText = QString::fromUtf8(fileData);
context.append(fileText); context.append(fileText);
} }
} }
context.append(baseText); context.append(baseText);
return context; return context;
} }
void KateAiPluginView::generate() void KateAiPluginView::generate()
{ {
qDebug()<<activeDocument()->mimeType(); qDebug()<<activeDocument()->mimeType();
if(m_webSocket && m_webSocket->isValid()) if(m_webSocket && m_webSocket->isValid())
{ {
KTextEditor::Cursor cursor = getCurrentCursor(); KTextEditor::Cursor cursor = getCurrentCursor();
QPointer<KTextEditor::Document> document = activeDocument(); QPointer<KTextEditor::Document> document = activeDocument();
QString text = assembleContext(document, cursor); QString text = assembleContext(document, cursor);
int id = QRandomGenerator::global()->bounded(0, std::numeric_limits<int>::max()); int id = QRandomGenerator::global()->bounded(0, std::numeric_limits<int>::max());
QJsonObject json; QJsonObject json;
json[QStringLiteral("action")] = QStringLiteral("infer"); json[QStringLiteral("action")] = QStringLiteral("infer");
json[QStringLiteral("request_id")] = id; json[QStringLiteral("request_id")] = id;
json[QStringLiteral("text")] = text; json[QStringLiteral("text")] = text;
json[QStringLiteral("max_new_tokens")] = 50; json[QStringLiteral("max_new_tokens")] = 50;
json[QStringLiteral("stream")] = false; json[QStringLiteral("stream")] = false;
QJsonDocument jsonDocument(json); QJsonDocument jsonDocument(json);
QString requestText = QString::fromUtf8(jsonDocument.toJson(QJsonDocument::JsonFormat::Compact)); QString requestText = QString::fromUtf8(jsonDocument.toJson(QJsonDocument::JsonFormat::Compact));
qDebug()<<__func__<<' '<<requestText; qDebug()<<__func__<<' '<<requestText;
m_webSocket->sendTextMessage(requestText); m_webSocket->sendTextMessage(requestText);
m_requests.insert(id, {cursor, document}); m_requests.insert(id, {cursor, document});
} }
else else
{ {
QMessageBox box; QMessageBox box;
box.setText(i18n("The AI server is not connected.")); box.setText(i18n("The AI server is not connected."));
box.setInformativeText(i18n("would you like to try and reconnect?")); box.setInformativeText(i18n("would you like to try and reconnect?"));
box.setStandardButtons(QMessageBox::Yes | QMessageBox::No); box.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
box.setDefaultButton(QMessageBox::Yes); box.setDefaultButton(QMessageBox::Yes);
int ret = box.exec(); int ret = box.exec();
if(ret == QMessageBox::Yes) if(ret == QMessageBox::Yes)
reconnect(); reconnect();
} }
} }
KateAiPluginView::~KateAiPluginView() KateAiPluginView::~KateAiPluginView()
{ {
m_mainWindow->guiFactory()->removeClient(this); m_mainWindow->guiFactory()->removeClient(this);
} }
void KateAiPluginView::setInstruct(bool instruct) void KateAiPluginView::setInstruct(bool instruct)
{ {
m_useInstruct = instruct; m_useInstruct = instruct;
} }
#include "kateai.moc" #include "kateai.moc"

View File

@ -15,62 +15,61 @@
class KateAiPlugin : public KTextEditor::Plugin class KateAiPlugin : public KTextEditor::Plugin
{ {
Q_OBJECT Q_OBJECT
private: private:
QWebSocket m_webSocket; QWebSocket m_webSocket;
QUrl m_serverUrl; QUrl m_serverUrl;
private: private:
void onConnected(); void onConnected();
int configPages() const override int configPages() const override
{ {
return 1; return 1;
} }
KTextEditor::ConfigPage *configPage(int number = 0, QWidget *parent = nullptr) override; KTextEditor::ConfigPage *configPage(int number = 0, QWidget *parent = nullptr) override;
public: public:
explicit KateAiPlugin(QObject *parent = nullptr, const QList<QVariant> & = QList<QVariant>()); explicit KateAiPlugin(QObject *parent = nullptr, const QList<QVariant> & = QList<QVariant>());
~KateAiPlugin() override; ~KateAiPlugin() override;
QObject *createView(KTextEditor::MainWindow *mainWindow) override; QObject *createView(KTextEditor::MainWindow *mainWindow) override;
void readConfig(); void readConfig();
void reconnect(); void reconnect();
Q_SIGNAL void instructChanged(); Q_SIGNAL void instructChanged();
}; };
class KateAiPluginView : public QObject, public KXMLGUIClient class KateAiPluginView : public QObject, public KXMLGUIClient
{ {
Q_OBJECT Q_OBJECT
private: private:
struct Request struct Request
{ {
KTextEditor::Cursor cursor; KTextEditor::Cursor cursor;
QPointer<KTextEditor::Document> document; QPointer<KTextEditor::Document> document;
}; };
KTextEditor::MainWindow *m_mainWindow;
QPointer<QWebSocket> m_webSocket;
QHash<int, Request> m_requests;
bool m_useInstruct = false;
KTextEditor::MainWindow *m_mainWindow;
QPointer<QWebSocket> m_webSocket;
QHash<int, Request> m_requests;
bool m_useInstruct = false;
private: private:
void generate(); void generate();
void socketMessage(const QString& message); void socketMessage(const QString& message);
static QStringList getIncludePaths(const QString& text); static QStringList getIncludePaths(const QString& text);
QString assembleContext(QPointer<KTextEditor::Document> document, const KTextEditor::Cursor& cursor); QString assembleContext(QPointer<KTextEditor::Document> document, const KTextEditor::Cursor& cursor);
QPointer<KTextEditor::Document> activeDocument() const;
KTextEditor::Cursor getCurrentCursor() const;
QPointer<KTextEditor::Document> activeDocument() const;
KTextEditor::Cursor getCurrentCursor() const;
public: public:
KateAiPluginView(KateAiPlugin *plugin, KTextEditor::MainWindow *mainwindow, QPointer<QWebSocket> webSocket, bool instruct = false); KateAiPluginView(KateAiPlugin *plugin, KTextEditor::MainWindow *mainwindow, QPointer<QWebSocket> webSocket,
~KateAiPluginView() override; bool instruct = false);
void setInstruct(bool instruct); ~KateAiPluginView() override;
void setInstruct(bool instruct);
Q_SIGNAL void reconnect(); Q_SIGNAL void reconnect();
}; };

View File

@ -9,57 +9,57 @@
#include <qlabel.h> #include <qlabel.h>
KateAiConfigPage::KateAiConfigPage(QWidget *parent, KateAiPlugin *plugin) KateAiConfigPage::KateAiConfigPage(QWidget *parent, KateAiPlugin *plugin)
: KTextEditor::ConfigPage(parent) : KTextEditor::ConfigPage(parent)
, m_plugin(plugin) , m_plugin(plugin)
{ {
QVBoxLayout* layout = new QVBoxLayout(this); QVBoxLayout* layout = new QVBoxLayout(this);
layout->setContentsMargins(0, 0, 0, 0); layout->setContentsMargins(0, 0, 0, 0);
QHBoxLayout* lineLayout = new QHBoxLayout(this); QHBoxLayout* lineLayout = new QHBoxLayout(this);
QLabel* lineEditLabel = new QLabel(i18n("Url for the WebSockets ExLlama Ai server:"), this); QLabel* lineEditLabel = new QLabel(i18n("Url for the WebSockets ExLlama Ai server:"), this);
lineEditLabel->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed)); lineEditLabel->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed));
lineLayout->addWidget(lineEditLabel); lineLayout->addWidget(lineEditLabel);
lineLayout->addWidget(&lineUrl); lineLayout->addWidget(&lineUrl);
layout->addLayout(lineLayout); layout->addLayout(lineLayout);
btnCompletion.setText(i18n("Use the Ai to generate a completion")); btnCompletion.setText(i18n("Use the Ai to generate a completion"));
btnInstruct.setText(i18n("Use the Ai to insert a response to a instruction")); btnInstruct.setText(i18n("Use the Ai to insert a response to a instruction"));
layout->addWidget(&btnCompletion); layout->addWidget(&btnCompletion);
layout->addWidget(&btnInstruct); layout->addWidget(&btnInstruct);
layout->addStretch(); layout->addStretch();
reset(); reset();
} }
QString KateAiConfigPage::name() const QString KateAiConfigPage::name() const
{ {
return i18n("Ai"); return i18n("Ai");
} }
QString KateAiConfigPage::fullName() const QString KateAiConfigPage::fullName() const
{ {
return i18n("Ai Settings"); return i18n("Ai Settings");
} }
QIcon KateAiConfigPage::icon() const QIcon KateAiConfigPage::icon() const
{ {
return QIcon::fromTheme(QStringLiteral("text-x-generic")); return QIcon::fromTheme(QStringLiteral("text-x-generic"));
} }
void KateAiConfigPage::apply() void KateAiConfigPage::apply()
{ {
KConfigGroup config(KSharedConfig::openConfig(), "Ai"); KConfigGroup config(KSharedConfig::openConfig(), "Ai");
config.writeEntry("Url", lineUrl.text()); config.writeEntry("Url", lineUrl.text());
config.writeEntry("Instruct", btnInstruct.isChecked()); config.writeEntry("Instruct", btnInstruct.isChecked());
config.sync(); config.sync();
m_plugin->readConfig(); m_plugin->readConfig();
} }
void KateAiConfigPage::reset() void KateAiConfigPage::reset()
{ {
KConfigGroup config(KSharedConfig::openConfig(), "Ai"); KConfigGroup config(KSharedConfig::openConfig(), "Ai");
lineUrl.setText(config.readEntry("Url", "ws://localhost:8642")); lineUrl.setText(config.readEntry("Url", "ws://localhost:8642"));
btnInstruct.setChecked(config.readEntry("Instruct", false)); btnInstruct.setChecked(config.readEntry("Instruct", false));
btnCompletion.setChecked(!btnInstruct.isChecked()); btnCompletion.setChecked(!btnInstruct.isChecked());
} }

View File

@ -8,26 +8,26 @@
class KateAiConfigPage : public KTextEditor::ConfigPage class KateAiConfigPage : public KTextEditor::ConfigPage
{ {
Q_OBJECT Q_OBJECT
private: private:
QLineEdit lineUrl; QLineEdit lineUrl;
QRadioButton btnCompletion; QRadioButton btnCompletion;
QRadioButton btnInstruct; QRadioButton btnInstruct;
KateAiPlugin* m_plugin; KateAiPlugin* m_plugin;
public: public:
explicit KateAiConfigPage(QWidget *parent = nullptr, KateAiPlugin *plugin = nullptr); explicit KateAiConfigPage(QWidget *parent = nullptr, KateAiPlugin *plugin = nullptr);
~KateAiConfigPage() override ~KateAiConfigPage() override
{ {
} }
QString name() const override; QString name() const override;
QString fullName() const override; QString fullName() const override;
QIcon icon() const override; QIcon icon() const override;
void apply() override; void apply() override;
void reset() override; void reset() override;
void defaults() override void defaults() override
{ {
} }
}; };