mirror of
https://github.com/OpenSpace/OpenSpace.git
synced 2026-01-06 03:29:44 -06:00
Move documentation generation to DocumentationEngine
Split Verifiers documentation method into documentation and type
This commit is contained in:
@@ -56,7 +56,7 @@ struct DocumentationEntry {
|
||||
Optional optional = Optional::No);
|
||||
|
||||
std::string key;
|
||||
std::shared_ptr<Verifier> tester;
|
||||
std::shared_ptr<Verifier> verifier;
|
||||
bool optional;
|
||||
std::string documentation;
|
||||
};
|
||||
@@ -76,8 +76,6 @@ TestResult testSpecification(const Documentation& d, const ghoul::Dictionary& di
|
||||
void testSpecificationAndThrow(const Documentation& doc,
|
||||
const ghoul::Dictionary& dictionary, std::string component);
|
||||
|
||||
std::string generateDocumentation(const Documentation& d);
|
||||
|
||||
} // namespace documentation
|
||||
|
||||
using documentation::Documentation;
|
||||
|
||||
@@ -36,7 +36,8 @@ struct Verifier {
|
||||
|
||||
virtual bool test(const ghoul::Dictionary& dict, const std::string& key) const;
|
||||
|
||||
virtual std::string documentation() const = 0;
|
||||
virtual std::string type() const = 0;
|
||||
virtual std::string documentation() const;
|
||||
};
|
||||
|
||||
// General verifiers
|
||||
@@ -48,25 +49,25 @@ struct TemplateVerifier : public Verifier {
|
||||
struct BoolVerifier : public TemplateVerifier<bool> {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
struct DoubleVerifier : public TemplateVerifier<double> {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
struct IntVerifier : public TemplateVerifier<int> {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
struct StringVerifier : public TemplateVerifier<std::string> {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
struct TableVerifier : public TemplateVerifier<ghoul::Dictionary> {
|
||||
@@ -74,7 +75,7 @@ struct TableVerifier : public TemplateVerifier<ghoul::Dictionary> {
|
||||
|
||||
TestResult operator()(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
|
||||
std::vector<DocumentationEntry> doc;
|
||||
};
|
||||
@@ -85,21 +86,21 @@ template <typename T>
|
||||
struct Vector2Verifier : public TemplateVerifier<glm::tvec2<T>>, public VectorVerifier {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct Vector3Verifier : public TemplateVerifier<glm::tvec3<T>>, public VectorVerifier {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct Vector4Verifier : public TemplateVerifier<glm::tvec4<T>>, public VectorVerifier {
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string documentation() const override;
|
||||
std::string type() const override;
|
||||
};
|
||||
|
||||
// Operator Verifiers
|
||||
@@ -277,6 +278,7 @@ struct AndVerifier : public Verifier {
|
||||
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string type() const override;
|
||||
std::string documentation() const override;
|
||||
|
||||
std::shared_ptr<Verifier> a;
|
||||
@@ -288,6 +290,7 @@ struct OrVerifier : public Verifier {
|
||||
|
||||
bool test(const ghoul::Dictionary& dict, const std::string& key) const override;
|
||||
|
||||
std::string type() const override;
|
||||
std::string documentation() const override;
|
||||
|
||||
std::shared_ptr<Verifier> a;
|
||||
|
||||
@@ -37,10 +37,10 @@ bool Vector2Verifier<T>::test(const ghoul::Dictionary& d, const std::string& k)
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
std::string Vector2Verifier<T>::documentation() const {
|
||||
std::string Vector2Verifier<T>::type() const {
|
||||
using namespace std::string_literals;
|
||||
|
||||
return "Type: Vector2<"s + typeid(T).name() + ">";
|
||||
return "Vector2<"s + typeid(T).name() + ">";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -49,10 +49,10 @@ bool Vector3Verifier<T>::test(const ghoul::Dictionary& d, const std::string& k)
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
std::string Vector3Verifier<T>::documentation() const {
|
||||
std::string Vector3Verifier<T>::type() const {
|
||||
using namespace std::string_literals;
|
||||
|
||||
return "Type: Vector3<"s + typeid(T).name() + ">";
|
||||
return "Vector3<"s + typeid(T).name() + ">";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -61,10 +61,10 @@ bool Vector4Verifier<T>::test(const ghoul::Dictionary& d, const std::string& k)
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
std::string Vector4Verifier<T>::documentation() const {
|
||||
std::string Vector4Verifier<T>::type() const {
|
||||
using namespace std::string_literals;
|
||||
|
||||
return "Type: Vector4<"s + typeid(T).name() + ">";
|
||||
return "Vector4<"s + typeid(T).name() + ">";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -80,7 +80,7 @@ bool LessVerifier<T>::test(const ghoul::Dictionary& dict, const std::string& key
|
||||
|
||||
template <typename T>
|
||||
std::string LessVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Less than: " + std::to_string(value);
|
||||
return "Less than: " + std::to_string(value);
|
||||
}
|
||||
|
||||
|
||||
@@ -96,7 +96,7 @@ bool LessEqualVerifier<T>::test(const ghoul::Dictionary& dict, const std::string
|
||||
|
||||
template <typename T>
|
||||
std::string LessEqualVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Less or equal to: " + std::to_string(value);
|
||||
return "Less or equal to: " + std::to_string(value);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -111,7 +111,7 @@ bool GreaterVerifier<T>::test(const ghoul::Dictionary& dict, const std::string&
|
||||
|
||||
template <typename T>
|
||||
std::string GreaterVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Greater than: " + std::to_string(value);
|
||||
return "Greater than: " + std::to_string(value);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -126,7 +126,7 @@ bool GreaterEqualVerifier<T>::test(const ghoul::Dictionary& dict, const std::str
|
||||
|
||||
template <typename T>
|
||||
std::string GreaterEqualVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Greater or equal to: " + std::to_string(value);
|
||||
return "Greater or equal to: " + std::to_string(value);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -141,7 +141,7 @@ bool EqualVerifier<T>::test(const ghoul::Dictionary& dict, const std::string& ke
|
||||
|
||||
template <typename T>
|
||||
std::string EqualVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Equal to: " + std::to_string(value);
|
||||
return "Equal to: " + std::to_string(value);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -156,7 +156,7 @@ bool UnequalVerifier<T>::test(const ghoul::Dictionary& dict, const std::string&
|
||||
|
||||
template <typename T>
|
||||
std::string UnequalVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Unequal to: " + std::to_string(value);
|
||||
return "Unequal to: " + std::to_string(value);
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -179,7 +179,7 @@ bool InListVerifier<T>::test(const ghoul::Dictionary& dict, const std::string& k
|
||||
|
||||
template <typename T>
|
||||
std::string InListVerifier<T>::documentation() const {
|
||||
std::string result = T::documentation() + '\n' + "In list {";
|
||||
std::string result = "In list { ";
|
||||
|
||||
std::stringstream s;
|
||||
std::copy(values.begin(), values.end(), std::ostream_iterator<typename T::Type>(s, ","));
|
||||
@@ -188,7 +188,7 @@ std::string InListVerifier<T>::documentation() const {
|
||||
// We need to remove a trailing ',' at the end of the string
|
||||
result += joined.substr(0, joined.size() - 1);
|
||||
|
||||
result += "}";
|
||||
result += " }";
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -212,7 +212,7 @@ bool NotInListVerifier<T>::test(const ghoul::Dictionary& dict, const std::string
|
||||
|
||||
template <typename T>
|
||||
std::string NotInListVerifier<T>::documentation() const {
|
||||
std::string result = T::documentation() + '\n' + "Not in list {";
|
||||
std::string result = "Not in list { ";
|
||||
|
||||
std::stringstream s;
|
||||
std::copy(values.begin(), values.end(), std::ostream_iterator<typename T::Type>(s, ","));
|
||||
@@ -222,7 +222,7 @@ std::string NotInListVerifier<T>::documentation() const {
|
||||
result += joined.substr(0, joined.size() - 1);
|
||||
|
||||
|
||||
result += "}";
|
||||
result += " }";
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -247,8 +247,8 @@ bool InRangeVerifier<T>::test(const ghoul::Dictionary& d, const std::string& key
|
||||
|
||||
template <typename T>
|
||||
std::string InRangeVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "In range: (" + std::to_string(lower) + "," +
|
||||
std::to_string(upper) + ")";
|
||||
return "In range: ( " + std::to_string(lower) + "," +
|
||||
std::to_string(upper) + " )";
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
@@ -272,8 +272,8 @@ bool NotInRangeVerifier<T>::test(const ghoul::Dictionary& d, const std::string&
|
||||
|
||||
template <typename T>
|
||||
std::string NotInRangeVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + "Not in range: (" + std::to_string(lower) + "," +
|
||||
std::to_string(upper) + ")";
|
||||
return "Not in range: ( " + std::to_string(lower) + "," +
|
||||
std::to_string(upper) + " )";
|
||||
}
|
||||
|
||||
|
||||
@@ -291,7 +291,7 @@ bool AnnotationVerifier<T>::test(const ghoul::Dictionary& dict,
|
||||
|
||||
template <typename T>
|
||||
std::string AnnotationVerifier<T>::documentation() const {
|
||||
return T::documentation() + '\n' + annotation;
|
||||
return annotation;
|
||||
}
|
||||
|
||||
} // namespace documentation
|
||||
|
||||
@@ -48,7 +48,7 @@ SpecificationError::SpecificationError(TestResult result, std::string component)
|
||||
DocumentationEntry::DocumentationEntry(std::string key, Verifier* t, std::string doc,
|
||||
Optional optional)
|
||||
: key(std::move(key))
|
||||
, tester(std::move(t))
|
||||
, verifier(std::move(t))
|
||||
, documentation(std::move(doc))
|
||||
, optional(optional) {}
|
||||
|
||||
@@ -66,7 +66,7 @@ TestResult testSpecification(const Documentation& d, const ghoul::Dictionary& di
|
||||
for (const auto& p : d.entries) {
|
||||
if (p.key == Wildcard) {
|
||||
for (const std::string& key : dictionary.keys()) {
|
||||
Verifier& verifier = *(p.tester);
|
||||
Verifier& verifier = *(p.verifier);
|
||||
TestResult res = verifier(dictionary, key);
|
||||
if (!res.success) {
|
||||
result.success = false;
|
||||
@@ -84,7 +84,7 @@ TestResult testSpecification(const Documentation& d, const ghoul::Dictionary& di
|
||||
// if the key exists, it has to be correct, however
|
||||
continue;
|
||||
}
|
||||
Verifier& verifier = *(p.tester);
|
||||
Verifier& verifier = *(p.verifier);
|
||||
TestResult res = verifier(dictionary, p.key);
|
||||
if (!res.success) {
|
||||
result.success = false;
|
||||
@@ -124,22 +124,5 @@ void testSpecificationAndThrow(const Documentation& doc,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
std::string generateDocumentation(const Documentation& d) {
|
||||
using namespace std::string_literals;
|
||||
std::string result;
|
||||
|
||||
result += "Name: "s + d.name + '\n';
|
||||
for (const auto& p : d.entries) {
|
||||
result += p.key + '\n';
|
||||
result += "Optional: "s + (p.optional ? "true" : "false") + '\n';
|
||||
result += p.tester->documentation() + '\n';
|
||||
result += '\n';
|
||||
result += p.documentation + '\n';
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
} // namespace documentation
|
||||
} // namespace openspace
|
||||
|
||||
@@ -24,6 +24,8 @@
|
||||
|
||||
#include <openspace/documentation/documentationengine.h>
|
||||
|
||||
#include <openspace/documentation/verifier.h>
|
||||
|
||||
#include <ghoul/misc/assert.h>
|
||||
|
||||
#include <fstream>
|
||||
@@ -31,6 +33,47 @@
|
||||
namespace openspace {
|
||||
namespace documentation {
|
||||
|
||||
|
||||
std::string generateTextDocumentation(const Documentation& d, int& indentLevel) {
|
||||
using namespace std::string_literals;
|
||||
|
||||
auto indentMessage = [&indentLevel](std::string prefix, std::string msg) {
|
||||
if (msg.empty()) {
|
||||
return ""s;
|
||||
}
|
||||
else {
|
||||
return std::string(indentLevel, '\t') + prefix + ": " + msg + '\n';
|
||||
}
|
||||
};
|
||||
std::string result;
|
||||
|
||||
result += indentMessage("Name", d.name);
|
||||
if (!d.name.empty()) {
|
||||
++indentLevel;
|
||||
}
|
||||
for (const auto& p : d.entries) {
|
||||
result += indentMessage("Key", (p.key == "*") ? p.key : "\"" + p.key + "\"");
|
||||
result += indentMessage("Optional", (p.optional ? "true" : "false"));
|
||||
result += indentMessage("Type", p.verifier->type());
|
||||
result += indentMessage("Restrictions", p.verifier->documentation());
|
||||
TableVerifier* tv = dynamic_cast<TableVerifier*>(p.verifier.get());
|
||||
if (tv) {
|
||||
// We have a TableVerifier, so we need to recurse
|
||||
++indentLevel;
|
||||
result += generateTextDocumentation(tv->doc, indentLevel);
|
||||
result = result.substr(0, result.size() - 2);
|
||||
--indentLevel;
|
||||
}
|
||||
result += indentMessage("Documentation", p.documentation);
|
||||
result += "\n\n";
|
||||
}
|
||||
if (!d.name.empty()) {
|
||||
--indentLevel;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void DocumentationEngine::writeDocumentation(const std::string& f, const std::string& t) {
|
||||
if (t == "text") {
|
||||
std::ofstream file;
|
||||
@@ -38,7 +81,8 @@ void DocumentationEngine::writeDocumentation(const std::string& f, const std::st
|
||||
file.open(f);
|
||||
|
||||
for (const Documentation& d : _documentations) {
|
||||
file << documentation::generateDocumentation(d) << std::endl << std::endl;
|
||||
int indent = 0;
|
||||
file << documentation::generateTextDocumentation(d, indent) << std::endl << std::endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -90,20 +90,24 @@ bool Verifier::test(const ghoul::Dictionary& dict, const std::string& key) const
|
||||
return false;
|
||||
};
|
||||
|
||||
std::string Verifier::documentation() const {
|
||||
return "";
|
||||
}
|
||||
|
||||
bool BoolVerifier::test(const ghoul::Dictionary& dict, const std::string& key) const {
|
||||
return dict.hasKeyAndValue<Type>(key);
|
||||
}
|
||||
|
||||
std::string BoolVerifier::documentation() const {
|
||||
return "Type: Boolean";
|
||||
std::string BoolVerifier::type() const {
|
||||
return "Boolean";
|
||||
}
|
||||
|
||||
bool DoubleVerifier::test(const ghoul::Dictionary & dict, const std::string & key) const {
|
||||
return dict.hasKeyAndValue<Type>(key);
|
||||
}
|
||||
|
||||
std::string DoubleVerifier::documentation() const {
|
||||
return "Type: Double";
|
||||
std::string DoubleVerifier::type() const {
|
||||
return "Double";
|
||||
}
|
||||
|
||||
bool IntVerifier::test(const ghoul::Dictionary & dict, const std::string & key) const {
|
||||
@@ -124,16 +128,16 @@ bool IntVerifier::test(const ghoul::Dictionary & dict, const std::string & key)
|
||||
}
|
||||
}
|
||||
|
||||
std::string IntVerifier::documentation() const {
|
||||
return "Type: Integer";
|
||||
std::string IntVerifier::type() const {
|
||||
return "Integer";
|
||||
}
|
||||
|
||||
bool StringVerifier::test(const ghoul::Dictionary & dict, const std::string & key) const {
|
||||
return dict.hasKeyAndValue<Type>(key);
|
||||
}
|
||||
|
||||
std::string StringVerifier::documentation() const {
|
||||
return "Type: String";
|
||||
std::string StringVerifier::type() const {
|
||||
return "String";
|
||||
}
|
||||
|
||||
TableVerifier::TableVerifier(std::vector<DocumentationEntry> d)
|
||||
@@ -156,19 +160,26 @@ TestResult TableVerifier::operator()(const ghoul::Dictionary& dict,
|
||||
return { dict.hasKeyAndValue<Type>(key), { key } };
|
||||
}
|
||||
|
||||
std::string TableVerifier::documentation() const {
|
||||
return "Type: Table" + '\n' + generateDocumentation(doc);
|
||||
std::string TableVerifier::type() const {
|
||||
return "Table";
|
||||
}
|
||||
|
||||
AndVerifier::AndVerifier(Verifier* a, Verifier* b)
|
||||
: a(a)
|
||||
, b(b)
|
||||
{}
|
||||
{
|
||||
ghoul_assert(a->type() == b->type(), "Cannot use AndVerifier with different types");
|
||||
}
|
||||
|
||||
bool AndVerifier::test(const ghoul::Dictionary& dict, const std::string& key) const {
|
||||
return a->test(dict, key) && b->test(dict, key);
|
||||
}
|
||||
|
||||
std::string AndVerifier::type() const {
|
||||
// It does not matter which type we choose as they both have to be the same
|
||||
return a->type();
|
||||
}
|
||||
|
||||
std::string AndVerifier::documentation() const {
|
||||
return a->documentation() + " and " + b->documentation();
|
||||
}
|
||||
@@ -182,6 +193,15 @@ bool OrVerifier::test(const ghoul::Dictionary& dict, const std::string& key) con
|
||||
return a->test(dict, key) || b->test(dict, key);
|
||||
}
|
||||
|
||||
std::string OrVerifier::type() const {
|
||||
if (a->type() != b->type()) {
|
||||
return a->type() + " or " + b->type();
|
||||
}
|
||||
else {
|
||||
return a->type();
|
||||
}
|
||||
}
|
||||
|
||||
std::string OrVerifier::documentation() const {
|
||||
return a->documentation() + " or " + b->documentation();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user