refactor: move saving of screen aliases to general deskflow.conf
This commit is contained in:
parent
2d5cf33f16
commit
8010d8a8b2
6 changed files with 61 additions and 104 deletions
|
|
@ -162,6 +162,15 @@ This section contains options used when in server mode it will begin with `[serv
|
||||||
|
|
||||||
- You can use both the ''switchDelay'' and ''switchDoubleTap'' options at the same time. Deskflow will switch when either requirement is satisfied.
|
- You can use both the ''switchDelay'' and ''switchDoubleTap'' options at the same time. Deskflow will switch when either requirement is satisfied.
|
||||||
|
|
||||||
|
### Screen Settings
|
||||||
|
|
||||||
|
Each screen will have a section where its configuration will be stored, if the screen was named "foo" the section will be named `[screen_foo]`
|
||||||
|
|
||||||
|
|Option | Valid Values |Description|
|
||||||
|
|:-------------------|:------------------:|:-----------|
|
||||||
|
| aliases | Comma separated list of hostnames | Names here will be used as alternatives for the computer. Names must be valid hostnames. |
|
||||||
|
|
||||||
|
|
||||||
### InternalConfig
|
### InternalConfig
|
||||||
|
|
||||||
This section contains options used when in server mode it will begin with `[internalConfig]`
|
This section contains options used when in server mode it will begin with `[internalConfig]`
|
||||||
|
|
@ -184,7 +193,6 @@ hotkeys\1\keys\1\key=83
|
||||||
hotkeys\1\keys\size=1
|
hotkeys\1\keys\size=1
|
||||||
hotkeys\size=1
|
hotkeys\size=1
|
||||||
screens\1\name=
|
screens\1\name=
|
||||||
screens\10\aliasArray\size=0
|
|
||||||
screens\10\fixArray\1\fix=false
|
screens\10\fixArray\1\fix=false
|
||||||
screens\10\fixArray\2\fix=false
|
screens\10\fixArray\2\fix=false
|
||||||
screens\10\fixArray\3\fix=false
|
screens\10\fixArray\3\fix=false
|
||||||
|
|
@ -214,7 +222,6 @@ screens\3\name=
|
||||||
screens\4\name=
|
screens\4\name=
|
||||||
screens\5\name=
|
screens\5\name=
|
||||||
screens\6\name=
|
screens\6\name=
|
||||||
screens\7\aliasArray\size=0
|
|
||||||
screens\7\fixArray\1\fix=false
|
screens\7\fixArray\1\fix=false
|
||||||
screens\7\fixArray\2\fix=false
|
screens\7\fixArray\2\fix=false
|
||||||
screens\7\fixArray\3\fix=false
|
screens\7\fixArray\3\fix=false
|
||||||
|
|
@ -234,7 +241,6 @@ screens\7\switchCornerArray\3\switchCorner=false
|
||||||
screens\7\switchCornerArray\4\switchCorner=false
|
screens\7\switchCornerArray\4\switchCorner=false
|
||||||
screens\7\switchCornerArray\size=4
|
screens\7\switchCornerArray\size=4
|
||||||
screens\7\switchCornerSize=0
|
screens\7\switchCornerSize=0
|
||||||
screens\8\aliasArray\size=0
|
|
||||||
screens\8\fixArray\1\fix=false
|
screens\8\fixArray\1\fix=false
|
||||||
screens\8\fixArray\2\fix=false
|
screens\8\fixArray\2\fix=false
|
||||||
screens\8\fixArray\3\fix=false
|
screens\8\fixArray\3\fix=false
|
||||||
|
|
@ -254,7 +260,6 @@ screens\8\switchCornerArray\3\switchCorner=false
|
||||||
screens\8\switchCornerArray\4\switchCorner=false
|
screens\8\switchCornerArray\4\switchCorner=false
|
||||||
screens\8\switchCornerArray\size=4
|
screens\8\switchCornerArray\size=4
|
||||||
screens\8\switchCornerSize=0
|
screens\8\switchCornerSize=0
|
||||||
screens\9\aliasArray\size=0
|
|
||||||
screens\9\fixArray\1\fix=false
|
screens\9\fixArray\1\fix=false
|
||||||
screens\9\fixArray\2\fix=false
|
screens\9\fixArray\2\fix=false
|
||||||
screens\9\fixArray\3\fix=false
|
screens\9\fixArray\3\fix=false
|
||||||
|
|
@ -292,11 +297,10 @@ end
|
||||||
Comments are introduced by ''#'' and continue to the end of the line. ''name'' must be one of the following:
|
Comments are introduced by ''#'' and continue to the end of the line. ''name'' must be one of the following:
|
||||||
|
|
||||||
* ''screens''
|
* ''screens''
|
||||||
* ''aliases''
|
|
||||||
* ''links''
|
* ''links''
|
||||||
* ''options''
|
* ''options''
|
||||||
|
|
||||||
The file is parsed top to bottom and names cannot be used before they've been defined in the <code>screens</code> or <code>aliases</code> sections. So the <code>links</code> and <code>aliases</code> must appear after the <code>screens</code> and <code>links</code> cannot refer to aliases unless the <code>aliases</code> appear before the <code>links</code>.
|
The file is parsed top to bottom and names cannot be used before they've been defined in the `screens` or as an alias in the general config. So the `links` must appear after the `screens`.
|
||||||
|
|
||||||
### The screens section
|
### The screens section
|
||||||
|
|
||||||
|
|
@ -333,21 +337,6 @@ A computer can have the following options:
|
||||||
|meta| shift ctrl alt meta super none | Map the server's meta modifer to different key on a client computer|
|
|meta| shift ctrl alt meta super none | Map the server's meta modifer to different key on a client computer|
|
||||||
|super| shift ctrl alt meta super none | Map the server's super modifer to different key on a client computer|
|
|super| shift ctrl alt meta super none | Map the server's super modifer to different key on a client computer|
|
||||||
|
|
||||||
### aliases section
|
|
||||||
|
|
||||||
''args'' is a list of computer names just like in the ''screens'' section except each computer is followed by a list of aliases, one per line, not followed by a colon. An ''alias'' is a computer name and must be unique. When searching for computers each alias is equivalent to the computer name it aliases. So a client can connect using its canonical computer name or any of its aliases.
|
|
||||||
|
|
||||||
```
|
|
||||||
section: aliases
|
|
||||||
larry:
|
|
||||||
larry.stooges.com
|
|
||||||
curly:
|
|
||||||
shemp
|
|
||||||
end
|
|
||||||
```
|
|
||||||
|
|
||||||
Computer ''larry'' is also known as ''larry.stooges.com'' and can connect as either name. Computer ''curly'' is also known as ''shemp'' (hey, it's just an example).
|
|
||||||
|
|
||||||
### links secion
|
### links secion
|
||||||
|
|
||||||
''args'' is a list of computer names just like in the ''screens'' section except each computer is followed by a list of links, one per line. Each link has the form:
|
''args'' is a list of computer names just like in the ''screens'' section except each computer is followed by a list of links, one per line. Each link has the form:
|
||||||
|
|
@ -597,6 +586,8 @@ Additionally, a name of the form `\uXXXX` where ''XXXX'' is a hexadecimal number
|
||||||
|
|
||||||
### Example textual configuration file
|
### Example textual configuration file
|
||||||
|
|
||||||
|
The alias section is no longer in the server config
|
||||||
|
|
||||||
This example comes from doc/deskflow-basic.conf
|
This example comes from doc/deskflow-basic.conf
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
|
||||||
|
|
@ -116,11 +116,12 @@ void Settings::cleanSettings()
|
||||||
m_settings->remove(key);
|
m_settings->remove(key);
|
||||||
if (key.startsWith(QStringLiteral("internalConfig")))
|
if (key.startsWith(QStringLiteral("internalConfig")))
|
||||||
continue;
|
continue;
|
||||||
if (!m_validKeys.contains(key))
|
if (const auto group = key.mid(0, key.indexOf('/')); !m_validKeys.contains(key) && m_validGroup.contains(group))
|
||||||
m_settings->remove(key);
|
m_settings->remove(key);
|
||||||
if (m_settings->value(key).toString().isEmpty())
|
if (!m_settings->value(key).canConvert<QStringList>() && m_settings->value(key).toString().isEmpty()) {
|
||||||
m_settings->remove(key);
|
m_settings->remove(key);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Settings::cleanStateSettings()
|
void Settings::cleanStateSettings()
|
||||||
|
|
|
||||||
|
|
@ -123,6 +123,11 @@ public:
|
||||||
inline static const auto XdpRestoreToken = QStringLiteral("server/xdpRestoreToken");
|
inline static const auto XdpRestoreToken = QStringLiteral("server/xdpRestoreToken");
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct Screen
|
||||||
|
{
|
||||||
|
inline static const auto Aliases = QStringLiteral("screen_%1/aliases");
|
||||||
|
};
|
||||||
|
|
||||||
// Enums types used in settings
|
// Enums types used in settings
|
||||||
// The use of enum classes is not use for these
|
// The use of enum classes is not use for these
|
||||||
// enum classes are more specific when used with QVariant
|
// enum classes are more specific when used with QVariant
|
||||||
|
|
@ -166,6 +171,7 @@ public:
|
||||||
static NetworkProtocol networkProtocol();
|
static NetworkProtocol networkProtocol();
|
||||||
static void save(bool emitSaving = true);
|
static void save(bool emitSaving = true);
|
||||||
static QStringList validKeys();
|
static QStringList validKeys();
|
||||||
|
static QStringList validGroups();
|
||||||
static QString portableSettingsFile();
|
static QString portableSettingsFile();
|
||||||
|
|
||||||
Q_SIGNALS:
|
Q_SIGNALS:
|
||||||
|
|
@ -204,6 +210,17 @@ private:
|
||||||
std::shared_ptr<QSettingsProxy> m_settingsProxy;
|
std::shared_ptr<QSettingsProxy> m_settingsProxy;
|
||||||
|
|
||||||
// clang-format off
|
// clang-format off
|
||||||
|
inline static const QStringList m_validGroup = {
|
||||||
|
QStringLiteral("client")
|
||||||
|
, QStringLiteral("core")
|
||||||
|
, QStringLiteral("daemon")
|
||||||
|
, QStringLiteral("gui")
|
||||||
|
, QStringLiteral("log")
|
||||||
|
, QStringLiteral("security")
|
||||||
|
, QStringLiteral("server")
|
||||||
|
, QStringLiteral("internalConfig")
|
||||||
|
};
|
||||||
|
|
||||||
inline static const QStringList m_validKeys = {
|
inline static const QStringList m_validKeys = {
|
||||||
Settings::Client::DynamicConnectionRetry
|
Settings::Client::DynamicConnectionRetry
|
||||||
, Settings::Client::InvertYScroll
|
, Settings::Client::InvertYScroll
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@
|
||||||
|
|
||||||
#include "Screen.h"
|
#include "Screen.h"
|
||||||
#include "config/ScreenConfig.h"
|
#include "config/ScreenConfig.h"
|
||||||
|
#include <common/Settings.h>
|
||||||
|
|
||||||
using enum ScreenConfig::Modifier;
|
using enum ScreenConfig::Modifier;
|
||||||
using enum ScreenConfig::SwitchCorner;
|
using enum ScreenConfig::SwitchCorner;
|
||||||
|
|
@ -20,29 +21,34 @@ Screen::Screen(const QString &name)
|
||||||
|
|
||||||
void Screen::loadSettings(QSettingsProxy &settings)
|
void Screen::loadSettings(QSettingsProxy &settings)
|
||||||
{
|
{
|
||||||
setName(settings.value("name").toString());
|
const auto name = settings.value("name").toString();
|
||||||
|
setName(name);
|
||||||
|
|
||||||
if (name().isEmpty())
|
if (name.isEmpty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
setSwitchCornerSize(settings.value("switchCornerSize").toInt());
|
setSwitchCornerSize(settings.value("switchCornerSize").toInt());
|
||||||
|
|
||||||
readSettings(settings, aliases(), "alias", QString(""));
|
|
||||||
readSettings(settings, modifiers(), "modifier", static_cast<int>(DefaultMod), static_cast<int>(NumModifiers));
|
readSettings(settings, modifiers(), "modifier", static_cast<int>(DefaultMod), static_cast<int>(NumModifiers));
|
||||||
readSettings(settings, switchCorners(), "switchCorner", false, static_cast<int>(NumSwitchCorners));
|
readSettings(settings, switchCorners(), "switchCorner", false, static_cast<int>(NumSwitchCorners));
|
||||||
readSettings(settings, fixes(), "fix", 0, static_cast<int>(NumFixes));
|
readSettings(settings, fixes(), "fix", 0, static_cast<int>(NumFixes));
|
||||||
|
|
||||||
|
m_Aliases = Settings::value(Settings::Screen::Aliases.arg(name)).toStringList();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Screen::saveSettings(QSettingsProxy &settings) const
|
void Screen::saveSettings(QSettingsProxy &settings) const
|
||||||
{
|
{
|
||||||
settings.setValue("name", name());
|
|
||||||
|
|
||||||
if (name().isEmpty())
|
const auto screenName = name();
|
||||||
|
settings.setValue("name", screenName);
|
||||||
|
|
||||||
|
if (screenName.isEmpty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
Settings::setValue(Settings::Screen::Aliases.arg(screenName), m_Aliases);
|
||||||
|
|
||||||
settings.setValue("switchCornerSize", switchCornerSize());
|
settings.setValue("switchCornerSize", switchCornerSize());
|
||||||
|
|
||||||
writeSettings(settings, aliases(), "alias");
|
|
||||||
writeSettings(settings, modifiers(), "modifier");
|
writeSettings(settings, modifiers(), "modifier");
|
||||||
writeSettings(settings, switchCorners(), "switchCorner");
|
writeSettings(settings, switchCorners(), "switchCorner");
|
||||||
writeSettings(settings, fixes(), "fix");
|
writeSettings(settings, fixes(), "fix");
|
||||||
|
|
@ -73,18 +79,6 @@ QString Screen::screensSection() const
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
|
||||||
QString Screen::aliasesSection() const
|
|
||||||
{
|
|
||||||
QString out;
|
|
||||||
if (!aliases().isEmpty()) {
|
|
||||||
out = QStringLiteral("\t%1:\n").arg(name());
|
|
||||||
|
|
||||||
for (const QString &alias : aliases())
|
|
||||||
out.append(QStringLiteral("\t\t%1\n").arg(alias));
|
|
||||||
}
|
|
||||||
return out;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Screen::operator==(const Screen &screen) const
|
bool Screen::operator==(const Screen &screen) const
|
||||||
{
|
{
|
||||||
return m_Name == screen.m_Name && m_Aliases == screen.m_Aliases && m_Modifiers == screen.m_Modifiers &&
|
return m_Name == screen.m_Name && m_Aliases == screen.m_Aliases && m_Modifiers == screen.m_Modifiers &&
|
||||||
|
|
|
||||||
|
|
@ -167,15 +167,6 @@ QTextStream &operator<<(QTextStream &outStream, const ServerConfig &config)
|
||||||
|
|
||||||
outStream << "end" << Qt::endl << Qt::endl;
|
outStream << "end" << Qt::endl << Qt::endl;
|
||||||
|
|
||||||
outStream << "section: aliases" << Qt::endl;
|
|
||||||
|
|
||||||
for (const Screen &s : config.screens()) {
|
|
||||||
if (!s.isNull())
|
|
||||||
outStream << s.aliasesSection();
|
|
||||||
}
|
|
||||||
|
|
||||||
outStream << "end" << Qt::endl << Qt::endl;
|
|
||||||
|
|
||||||
outStream << "section: links" << Qt::endl;
|
outStream << "section: links" << Qt::endl;
|
||||||
|
|
||||||
for (int i = 0; const auto &screen : config.screens()) {
|
for (int i = 0; const auto &screen : config.screens()) {
|
||||||
|
|
|
||||||
|
|
@ -46,6 +46,11 @@ bool Config::addScreen(const std::string &name)
|
||||||
// add name
|
// add name
|
||||||
m_nameToCanonicalName.try_emplace(name, name);
|
m_nameToCanonicalName.try_emplace(name, name);
|
||||||
|
|
||||||
|
// add aliases
|
||||||
|
const auto aliases = Settings::value(Settings::Screen::Aliases.arg(QString::fromStdString(name))).toStringList();
|
||||||
|
for (const auto &alias : aliases)
|
||||||
|
m_nameToCanonicalName.try_emplace(alias.toStdString(), name);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -88,6 +93,12 @@ bool Config::renameScreen(const std::string &oldName, const std::string &newName
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Update Settings
|
||||||
|
const auto aliasList = Settings::value(Settings::Screen::Aliases.arg(QString::fromStdString(oldName))).toStringList();
|
||||||
|
if (aliasList.isEmpty())
|
||||||
|
return true;
|
||||||
|
Settings::setValue(Settings::Screen::Aliases.arg(QString::fromStdString(oldName)), QVariant());
|
||||||
|
Settings::setValue(Settings::Screen::Aliases.arg(QString::fromStdString(newName)), aliasList);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -109,6 +120,7 @@ void Config::removeScreen(const std::string &name)
|
||||||
index->second.remove(nameObj);
|
index->second.remove(nameObj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Settings::setValue(Settings::Screen::Aliases.arg(QString::fromStdString(name)), QVariant());
|
||||||
// remove aliases (and canonical name)
|
// remove aliases (and canonical name)
|
||||||
for (auto iter = m_nameToCanonicalName.begin(); iter != m_nameToCanonicalName.end();) {
|
for (auto iter = m_nameToCanonicalName.begin(); iter != m_nameToCanonicalName.end();) {
|
||||||
if (iter->second == canonical) {
|
if (iter->second == canonical) {
|
||||||
|
|
@ -554,10 +566,10 @@ void Config::readSection(ConfigReadContext &s)
|
||||||
readSectionOptions(s);
|
readSectionOptions(s);
|
||||||
} else if (name == s_screens) {
|
} else if (name == s_screens) {
|
||||||
readSectionScreens(s);
|
readSectionScreens(s);
|
||||||
} else if (name == s_links) {
|
|
||||||
readSectionLinks(s);
|
|
||||||
} else if (name == s_aliases) {
|
} else if (name == s_aliases) {
|
||||||
readSectionAliases(s);
|
readSectionAliases(s);
|
||||||
|
} else if (name == s_links) {
|
||||||
|
readSectionLinks(s);
|
||||||
} else {
|
} else {
|
||||||
throw ServerConfigReadException(s, "unknown section name \"%{1}\"", name);
|
throw ServerConfigReadException(s, "unknown section name \"%{1}\"", name);
|
||||||
}
|
}
|
||||||
|
|
@ -827,39 +839,14 @@ void Config::readSectionLinks(ConfigReadContext &s)
|
||||||
|
|
||||||
void Config::readSectionAliases(ConfigReadContext &s)
|
void Config::readSectionAliases(ConfigReadContext &s)
|
||||||
{
|
{
|
||||||
|
qWarning(
|
||||||
|
) << "Your server config has an alias section. Alias have moved to the general config this section will no be "
|
||||||
|
"parsed.";
|
||||||
std::string line;
|
std::string line;
|
||||||
std::string screen;
|
|
||||||
while (s.readLine(line)) {
|
while (s.readLine(line)) {
|
||||||
// check for end of section
|
|
||||||
if (line == "end") {
|
if (line == "end") {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// see if it's the next screen
|
|
||||||
if (line[line.size() - 1] == ':') {
|
|
||||||
// strip :
|
|
||||||
screen = line.substr(0, line.size() - 1);
|
|
||||||
|
|
||||||
// verify we know about the screen
|
|
||||||
if (!isScreen(screen)) {
|
|
||||||
throw ServerConfigReadException(s, "unknown screen name \"%{1}\"", screen);
|
|
||||||
}
|
|
||||||
if (!isCanonicalName(screen)) {
|
|
||||||
throw ServerConfigReadException(s, "cannot use screen name alias here");
|
|
||||||
}
|
|
||||||
} else if (screen.empty()) {
|
|
||||||
throw ServerConfigReadException(s, "argument before first screen");
|
|
||||||
} else {
|
|
||||||
// verify validity of screen name
|
|
||||||
if (!isValidScreenName(line)) {
|
|
||||||
throw ServerConfigReadException(s, "invalid screen alias \"%{1}\"", line);
|
|
||||||
}
|
|
||||||
|
|
||||||
// add alias
|
|
||||||
if (!addAlias(screen, line)) {
|
|
||||||
throw ServerConfigReadException(s, "alias \"%{1}\" is already used", line);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
throw ServerConfigReadException(s, "unexpected end of aliases section");
|
throw ServerConfigReadException(s, "unexpected end of aliases section");
|
||||||
}
|
}
|
||||||
|
|
@ -1557,30 +1544,6 @@ std::ostream &operator<<(std::ostream &s, const Config &config)
|
||||||
}
|
}
|
||||||
s << "end" << std::endl;
|
s << "end" << std::endl;
|
||||||
|
|
||||||
// aliases section (if there are any)
|
|
||||||
if (config.m_map.size() != config.m_nameToCanonicalName.size()) {
|
|
||||||
// map canonical to alias
|
|
||||||
using CMNameMap = std::multimap<std::string, std::string, CaselessCmp>;
|
|
||||||
CMNameMap aliases;
|
|
||||||
for (auto index = config.m_nameToCanonicalName.begin(); index != config.m_nameToCanonicalName.end(); ++index) {
|
|
||||||
if (index->first != index->second) {
|
|
||||||
aliases.insert(std::make_pair(index->second, index->first));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// dump it
|
|
||||||
std::string screen;
|
|
||||||
s << "section: aliases" << std::endl;
|
|
||||||
for (CMNameMap::const_iterator index = aliases.begin(); index != aliases.end(); ++index) {
|
|
||||||
if (index->first != screen) {
|
|
||||||
screen = index->first;
|
|
||||||
s << "\t" << screen.c_str() << ":" << std::endl;
|
|
||||||
}
|
|
||||||
s << "\t\t" << index->second.c_str() << std::endl;
|
|
||||||
}
|
|
||||||
s << "end" << std::endl;
|
|
||||||
}
|
|
||||||
|
|
||||||
// options section
|
// options section
|
||||||
s << "section: options" << std::endl;
|
s << "section: options" << std::endl;
|
||||||
if (const Config::ScreenOptions *options = config.getOptions(""); options && options->size() > 0) {
|
if (const Config::ScreenOptions *options = config.getOptions(""); options && options->size() > 0) {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue