7 #include <QStringBuilder>
24 using namespace swift::misc::db;
28 namespace swift::misc::aviation
30 CAirlineIcaoCode::CAirlineIcaoCode(
const QString &airlineDesignator)
31 : m_designator(airlineDesignator.trimmed().toUpper())
33 if (m_designator.length() == 4) { this->
setDesignator(m_designator); }
37 const CCountry &country,
const QString &telephony,
bool virtualAirline,
39 : m_designator(airlineDesignator.trimmed().toUpper()), m_name(airlineName), m_telephonyDesignator(telephony),
40 m_country(country), m_isVa(virtualAirline), m_isOperating(operating)
42 if (m_designator.length() == 4) { this->
setDesignator(m_designator); }
48 return u
'V' % m_designator;
59 m_designator = icaoDesignator.trimmed().toUpper();
60 if (m_designator.length() == 4 && m_designator.startsWith(
"V"))
64 m_designator = m_designator.right(3);
91 if (designator.isEmpty() || m_designator.isEmpty()) {
return false; }
97 if (designator.isEmpty() || m_designator.isEmpty()) {
return false; }
103 if (iata.isEmpty() || m_iataCode.isEmpty()) {
return false; }
109 if (candidate.isEmpty()) {
return false; }
115 if (candidate.isEmpty()) {
return false; }
121 if (candidate.isEmpty() || m_telephonyDesignator.isEmpty()) {
return false; }
127 const QString cand(candidate.toUpper().trimmed());
128 if (this->
getName().contains(cand, Qt::CaseInsensitive) ||
138 if (candidate.isEmpty() || !this->hasName()) {
return false; }
139 auto simplifiedName =
141 auto it = std::search(simplifiedName.begin(), simplifiedName.end(), candidate.begin(), candidate.end(),
142 [](QChar a, QChar b) { return a.toUpper() == b.toUpper(); });
143 return it != simplifiedName.end();
161 return CIcons::StandardIconEmpty;
175 if (index.
isMyself()) {
return QVariant::fromValue(*
this); }
176 if (IDatastoreObjectWithIntegerKey::canHandleIndex(index))
178 return IDatastoreObjectWithIntegerKey::propertyByIndex(index);
183 case IndexAirlineDesignator:
return QVariant::fromValue(m_designator);
184 case IndexIataCode:
return QVariant::fromValue(m_iataCode);
185 case IndexAirlineCountryIso:
return QVariant::fromValue(this->
getCountryIso());
187 case IndexAirlineName:
return QVariant::fromValue(m_name);
188 case IndexTelephonyDesignator:
return QVariant::fromValue(m_telephonyDesignator);
189 case IndexIsVirtualAirline:
return QVariant::fromValue(m_isVa);
190 case IndexIsOperating:
return QVariant::fromValue(m_isOperating);
191 case IndexIsMilitary:
return QVariant::fromValue(m_isMilitary);
194 case IndexGroupName:
return QVariant::fromValue(this->
getGroupName());
195 case IndexGroupId:
return QVariant::fromValue(this->
getGroupId());
207 if (IDatastoreObjectWithIntegerKey::canHandleIndex(index))
209 IDatastoreObjectWithIntegerKey::setPropertyByIndex(index, variant);
215 case IndexAirlineDesignator: this->
setDesignator(variant.value<QString>());
break;
216 case IndexIataCode: this->
setIataCode(variant.value<QString>());
break;
218 case IndexAirlineName: this->
setName(variant.value<QString>());
break;
221 case IndexIsOperating: this->
setOperating(variant.toBool());
break;
222 case IndexIsMilitary: this->
setMilitary(variant.toBool());
break;
224 case IndexGroupName: this->
setGroupName(variant.toString());
break;
225 case IndexGroupId: this->
setGroupId(variant.toInt());
break;
232 if (index.
isMyself()) {
return m_designator.compare(compareValue.
getDesignator(), Qt::CaseInsensitive); }
233 if (IDatastoreObjectWithIntegerKey::canHandleIndex(index))
235 return IDatastoreObjectWithIntegerKey::comparePropertyByIndex(index, compareValue);
240 case IndexAirlineDesignator:
return m_designator.compare(compareValue.
getDesignator());
241 case IndexIataCode:
return m_iataCode.compare(compareValue.
getIataCode());
242 case IndexAirlineCountry:
244 case IndexDesignatorNameCountry:
246 case IndexAirlineName:
return m_name.compare(compareValue.
getName(), Qt::CaseInsensitive);
247 case IndexTelephonyDesignator:
252 case IndexGroupDesignator:
253 return m_groupDesignator.compare(compareValue.
getGroupDesignator(), Qt::CaseInsensitive);
254 case IndexGroupName:
return m_groupName.compare(compareValue.
getGroupName(), Qt::CaseInsensitive);
255 case IndexGroupId:
return Compare::compare(m_groupId, compareValue.
getGroupId());
258 Q_ASSERT_X(
false, Q_FUNC_INFO,
"No compare function");
281 if (airline.length() < 2 || airline.length() > 5) {
return false; }
282 const auto chars =
makeRange(airline.begin(), airline.end());
283 if (chars.containsBy([](QChar c) { return !c.isUpper() && !c.isDigit(); })) {
return false; }
289 if (iataCode.length() != 2) {
return false; }
295 static const QSet<QString> valid({
"VV",
"VM" });
301 QString n(candidate.trimmed().toUpper());
302 n = n.left(
indexOfChar(n, [](QChar c) {
return c.isSpace(); }));
303 return removeChars(n, [](QChar c) {
return !c.isLetterOrNumber(); });
318 const QString &message,
const QStringList &extraCategories,
321 if (!log) {
return; }
322 if (message.isEmpty()) {
return; }
335 if (callsign.
isEmpty()) {
return *
this; }
337 if (callsignAirline.isEmpty()) {
return *
this; }
338 if (callsignAirline == m_designator) {
return *
this; }
341 if (m_designator.isEmpty()) {
return callsignIcao; }
426 log, *
this, QStringLiteral(
"Same simplified name '%1': %2").arg(this->
getSimplifiedName()).arg(score));
433 return m_designator.isNull() && m_iataCode.isNull() && m_telephonyDesignator.isNull();
450 QString designator(json.value(prefix % u
"designator").toString());
456 const QString iata(json.value(prefix % u
"iata").toString());
457 const QString telephony(json.value(prefix % u
"callsign").toString());
458 const QString name(json.value(prefix % u
"name").toString());
459 const QString countryIso(json.value(prefix % u
"country").toString());
460 const QString countryName(json.value(prefix % u
"countryname").toString());
461 const QString groupName(json.value(prefix % u
"groupname").toString());
462 const QString groupDesignator(json.value(prefix % u
"groupdesignator").toString());
463 const int groupId(json.value(prefix % u
"groupid").toInt(-1));
464 const bool va = CDatastoreUtility::dbBoolStringToBool(json.value(prefix % u
"va").toString());
465 const bool operating = CDatastoreUtility::dbBoolStringToBool(json.value(prefix % u
"operating").toString());
466 const bool military = CDatastoreUtility::dbBoolStringToBool(json.value(prefix % u
"military").toString());
const QString & getName() const
Country name.
bool isValid() const
Valid?
int comparePropertyByIndex(CPropertyIndexRef index, const CCountry &compareValue) const
Compare for index.
QVariant propertyByIndex(CPropertyIndexRef index) const
Property by index.
IconIndex
Index for each icon, allows to send them via DBus, efficiently store them, etc.
static const QString & aviation()
Aviation specific.
A sequence of log categories.
static CLogCategoryList fromQStringList(const QStringList &stringList)
Convert a string list, such as that returned by toQStringList(), into a CLogCategoryList.
Non-owning reference to a CPropertyIndex with a subset of its features.
Q_REQUIRED_RESULT CPropertyIndexRef copyFrontRemoved() const
Copy with first element removed.
CastType frontCasted() const
First element casted to given type, usually the PropertIndex enum.
bool isMyself() const
Myself index, used with nesting.
void push_back(const T &value)
Appends an element at the end of the sequence.
Streamable status message, e.g.
constexpr static auto SeverityError
Status severities.
Status messages, e.g. from Core -> GUI.
QDateTime getUtcTimestamp() const
Get timestamp.
void setUtcTimestamp(const QDateTime ×tamp)
Set timestamp.
Value object for ICAO classification.
const QString & getGroupDesignator() const
Group designator.
QString getCombinedStringWithKey() const
Comined string with key.
void setMilitary(bool military)
Military, air force or such?
bool isVirtualAirline() const
Virtual airline.
static bool isValidAirlineDesignator(const QString &airline)
Valid designator?
static QSet< QString > specialValidDesignators()
Some special valid designator which do not fit standard rule (e.g. 3-letter code)
void setTelephonyDesignator(const QString &telephony)
Telephony designator such as "Speedbird".
void setOperating(bool operating)
Operating airline?
CAirlineIcaoCode()=default
Default constructor.
bool isNull() const
Null ICAO?
const QString & getCountryIso() const
Get country, e.g. "FR".
const QString & getIataCode() const
IATA code.
bool isContainedInSimplifiedName(const QString &candidate) const
Does simplified name contain the candidate.
void setGroupId(int id)
Group id.
QString getVDesignatorDbKey() const
Get VDesignator plus key.
void setPropertyByIndex(CPropertyIndexRef index, const QVariant &variant)
Set property by index.
bool matchesDesignator(const QString &designator) const
Matches designator string?
bool isMilitary() const
Military, air force or such?
static const CAirlineIcaoCode & null()
NULL object.
QString getSimplifiedName() const
Get a simplified upper case name for searching by removing all characters except A-Z.
const QString & getTelephonyDesignator() const
Telephony designator such as "Speedbird".
QString getDesignatorDbKey() const
Designator and DB key.
QVariant propertyByIndex(CPropertyIndexRef index) const
Property by index.
ColumnIndex
Properties by index.
QString convertToQString(bool i18n=false) const
Cast as QString.
bool hasValidCountry() const
Country?
void setVirtualAirline(bool va)
Virtual airline.
const QString & getDesignator() const
Get airline, e.g. "DLH".
bool hasIataCode() const
IATA code?
CStatusMessageList validate() const
Validate data.
static QString normalizeDesignator(const QString &candidate)
Normalize string as airline designator.
bool hasTelephonyDesignator() const
Telephony designator?
void setIataCode(const QString &iataCode)
Set IATA code.
bool hasCompleteData() const
Complete data.
bool hasValidDesignator() const
Airline designator available?
static CAirlineIcaoCode fromDatabaseJson(const QJsonObject &json, const QString &prefix=QString())
From our DB JSON.
void updateMissingParts(const CAirlineIcaoCode &otherIcaoCode)
Update missing parts.
void setName(const QString &name)
Set name.
bool matchesTelephonyDesignator(const QString &candidate) const
Matches telephony designator (aka callsign, not to be confused with CCallsign)
void setCountry(const CCountry &country)
Set country.
QString asHtmlSummary() const
As a brief HTML summary (e.g. used in tooltips)
bool matchesVDesignator(const QString &designator) const
Matches v-designator string?
CIcons::IconIndex toIcon() const
As icon, not implemented by all classes.
void setGroupDesignator(const QString &designator)
Group designator.
int calculateScore(const CAirlineIcaoCode &otherCode, CStatusMessageList *log=nullptr) const
Score against other code 0..100.
static bool isValidIataCode(const QString &iataCode)
Valid IATA code?
bool matchesNamesOrTelephonyDesignator(const QString &candidate) const
Relaxed check by name or telephony designator (aka callsign, not to be confused with CCallsign)
bool matchesVDesignatorOrIataCode(const QString &candidate) const
Matches IATA code or v-designator?
int getGroupId() const
Group id.
bool matchesDesignatorOrIataCode(const QString &candidate) const
Matches IATA code or designator?
void setDesignator(const QString &icaoDesignator)
Set airline, e.g. "DLH".
const QString & getGroupName() const
Group name.
const CCountry & getCountry() const
Get country, e.g. "FRANCE".
bool matchesIataCode(const QString &iata) const
Matches IATA code?
static CStatusMessage logMessage(const CAirlineIcaoCode &icaoCode, const QString &message, const QStringList &extraCategories={}, CStatusMessage::StatusSeverity s=CStatusMessage::SeverityInfo)
Specialized log message for matching / reverse lookup.
static void addLogDetailsToList(CStatusMessageList *log, const CAirlineIcaoCode &icao, const QString &message, const QStringList &extraCategories={}, CStatusMessage::StatusSeverity s=CStatusMessage::SeverityInfo)
Specialized log for matching / reverse lookup.
int comparePropertyByIndex(CPropertyIndexRef index, const CAirlineIcaoCode &compareValue) const
Compare for index.
void setGroupName(const QString &name)
Group name.
QString getDesignatorNameCountry() const
Combined string designator, name, country.
QString getVDesignator() const
Get airline, e.g. "DLH", but "VMVA" for virtual airlines.
const QString & getName() const
Get name, e.g. "Lufthansa".
CAirlineIcaoCode thisOrCallsignCode(const CCallsign &callsign) const
What is better, the callsign airline code or this code. Return the better one.
bool isOperating() const
Operating?
QString getNameWithKey() const
Name plus key, e.g. "Lufthansa (3421)".
bool hasSimplifiedName() const
Has simplified airline name?
bool hasName() const
Has (airline) name?
Value object encapsulating information of a callsign.
bool isEmpty() const
Is empty?
QString getAirlinePrefix() const
Airline suffix (e.g. DLH1234 -> DLH) if applicable.
int getDbKey() const
Get DB key.
bool isLoadedFromDb() const
Loaded from DB.
static bool existsKey(const QJsonObject &json, const QString &prefix=QString())
Is a key available?
void setDbKey(int key)
Set the DB key.
bool isDbEqual(const IDatastoreObjectWithIntegerKey &other) const
Same DB key and hence equal.
QString getDbKeyAsStringInParentheses(const QString &prefix={}) const
Db key in parentheses, e.g. "(3)".
void setKeyVersionTimestampFromDatabaseJson(const QJsonObject &json, const QString &prefix=QString())
Set key and timestamp values.
bool hasValidDbKey() const
Has valid DB key.
void setPropertyByIndex(CPropertyIndexRef index, const QVariant &variant)
Set property by index.
QVariant propertyByIndex(CPropertyIndexRef index) const
Property by index.
Free functions in swift::misc.
SWIFT_MISC_EXPORT QString simplifyNameForSearch(const QString &name)
Get a simplified upper case name for searching by removing all characters except A-Z.
T::const_iterator begin(const LockFreeReader< T > &reader)
Non-member begin() and end() for so LockFree containers can be used in ranged for loops.
QString removeChars(const QString &s, F predicate)
Return a string with characters removed that match the given predicate.
auto makeRange(I begin, I2 end) -> CRange< I >
Returns a CRange constructed from begin and end iterators of deduced types.
SWIFT_MISC_EXPORT bool caseInsensitiveStringCompare(const QString &c1, const QString &c2)
Case insensitive string compare.
int indexOfChar(const QString &s, F predicate)
Index of first character in the string matching the given predicate, or -1 if not found.
T::const_iterator end(const LockFreeReader< T > &reader)
Non-member begin() and end() for so LockFree containers can be used in ranged for loops.
StatusSeverity
Status severities.
SWIFT_MISC_EXPORT const QString & boolToYesNo(bool v)
Bool to yes/no.
#define SWIFT_DEFINE_VALUEOBJECT_MIXINS(Namespace, Class)
Explicit template definition of mixins for a CValueObject subclass.