Start supporting dict and json types.

This commit is contained in:
jmsgrogan 2024-01-03 09:13:23 +00:00
parent 94fcc42aed
commit 5183aa821a
32 changed files with 288 additions and 247 deletions

View file

@ -1,7 +0,0 @@
add_subdirectory(base)
add_subdirectory(console)
add_subdirectory(media)
add_subdirectory(publishing)
add_subdirectory(rendering)
add_subdirectory(ui)
add_subdirectory(web)

View file

@ -12,6 +12,7 @@ Status BuildLibrary::scan()
{ {
LOG_INFO("Scanning build file at: " << m_build_config); LOG_INFO("Scanning build file at: " << m_build_config);
const auto search_dir = m_build_config.parent_path(); const auto search_dir = m_build_config.parent_path();
m_name = search_dir.stem().str();
STATUS_CHECK(Directory::getFilesWithExtension(search_dir, STATUS_CHECK(Directory::getFilesWithExtension(search_dir,
".cpp", ".cpp",
@ -25,6 +26,11 @@ Status BuildLibrary::scan()
return {}; return {};
} }
const String& BuildLibrary::get_name() const
{
return m_name;
}
const Vector<FileSystemPath>& BuildLibrary::get_sources() const const Vector<FileSystemPath>& BuildLibrary::get_sources() const
{ {
return m_sources; return m_sources;

View file

@ -16,6 +16,8 @@ public:
const Vector<FileSystemPath>& get_include_dirs() const; const Vector<FileSystemPath>& get_include_dirs() const;
const String& get_name() const;
private: private:
FileSystemPath m_build_config; FileSystemPath m_build_config;
Vector<FileSystemPath> m_sources; Vector<FileSystemPath> m_sources;

View file

@ -26,18 +26,18 @@ BuildSession::BuildSession(const String& source_dir,
Status BuildSession::scan() Status BuildSession::scan()
{ {
LOG_INFO("Scanning sources at:" << m_source_dir); LOG_INFO("Scanning sources at:" << m_source_dir);
Vector<FileSystemPath> ini_files; Vector<FileSystemPath> yaml_files;
STATUS_CHECK(Directory::getFilesWithExtension( STATUS_CHECK(Directory::getFilesWithExtension(
m_source_dir, m_source_dir,
".ini", ".yaml",
ini_files, yaml_files,
true), "Error looking for build files"); true), "Error looking for build files");
for(const auto& ini_file : ini_files) for(const auto& yaml_file : yaml_files)
{ {
if (ini_file.file_name() == "build") if (yaml_file.file_name() == "build")
{ {
STATUS_CHECK(add_library(ini_file), STATUS_CHECK(add_library(yaml_file),
"Error adding library"); "Error adding library");
} }
} }
@ -55,10 +55,16 @@ Status BuildSession::add_library(const FileSystemPath& config_path)
Status BuildSession::build() Status BuildSession::build()
{ {
LOG_INFO("Creating dir: " << m_build_dir);
Directory::create(m_build_dir, true); Directory::create(m_build_dir, true);
for(auto& library : m_libraries) for(auto& library : m_libraries)
{ {
const auto run_status = compile_library(library); auto run_status = compile_library(library);
if (!run_status.ok())
{
return run_status;
}
run_status = create_archive(library);
if (!run_status.ok()) if (!run_status.ok())
{ {
return run_status; return run_status;
@ -82,6 +88,25 @@ Status BuildSession::compile_library(BuildLibrary& lib)
return {}; return {};
} }
Status BuildSession::create_archive(BuildLibrary& lib)
{
Vector<String> args;
args.push_back("rcs");
auto name = "lib" + lib.get_name() + ".a";
args.push_back(name);
for(const auto& source : lib.get_sources())
{
const auto output_path = m_build_dir / source.file_name();
const auto output_file = output_path.str() + ".o";
args.push_back(output_file);
}
LOG_INFO("Archiving " << name);
return Process::launch(m_archive_command, args);
}
Status BuildSession::compile_source_file(const FileSystemPath& source, Status BuildSession::compile_source_file(const FileSystemPath& source,
const BuildLibrary& lib) const BuildLibrary& lib)
{ {

View file

@ -23,7 +23,10 @@ private:
void add_include_dirs(Vector<String>& args, const BuildLibrary& lib); void add_include_dirs(Vector<String>& args, const BuildLibrary& lib);
Status create_archive(BuildLibrary& lib);
String m_compiler_command{"/usr/bin/g++"}; String m_compiler_command{"/usr/bin/g++"};
String m_archive_command{"/usr/bin/ar"};
Vector<String> m_compiler_flags; Vector<String> m_compiler_flags;
FileSystemPath m_source_dir; FileSystemPath m_source_dir;
FileSystemPath m_build_dir; FileSystemPath m_build_dir;

View file

@ -0,0 +1,20 @@
#pragma once
class Number
{
public:
enum class Type
{
HEX,
INT,
FLOAT,
FRACTION,
EXPONENT
};
Number() = default;
private:
Type m_type{Type::INT};
unsigned m_value{0};
};

View file

@ -1,57 +1,65 @@
#include "Dictionary.h" #include "Dictionary.h"
bool Dictionary::hasKey(const String& key) const Dictionary::Dictionary(const String& item)
: mType(Type::SCALAR),
mScalarType(ScalarType::STRING),
mStringVal(item)
{ {
return hasStringKey(key) || hasDictKey(key);
} }
bool Dictionary::hasStringKey(const String& key) const void Dictionary::addItem(const String& key, Ptr<Dictionary> dict)
{ {
return mStringData.has_key(key); mMapVal.insert(key, std::move(dict));
} }
bool Dictionary::hasDictKey(const String& key) const void Dictionary::addItem(const String& key, const String& item)
{ {
return mDictData.has_key(key); mMapVal.insert(key, Ptr<Dictionary>::create(item));
} }
Vector<String> Dictionary::getStringKeys() const Vector<String> Dictionary::getKeys() const
{ {
Vector<String> keys; Vector<String> keys;
for (const auto& item : mStringData) for (const auto& item : mMapVal)
{ {
keys.push_back(item.key()); keys.push_back(item.key());
} }
return keys; return keys;
} }
Vector<String> Dictionary::getDictKeys() const Dictionary* Dictionary::getItemAsMap(const String& key) const
{ {
Vector<String> keys; if (isMap())
for (const auto& item : mDictData)
{ {
keys.push_back(item.key()); return (*mMapVal.find(key)).value().get();
} }
return keys;
}
Dictionary* Dictionary::getDict(const String& key) const
{
//return (*mDictData.find(key)).value().get();
return nullptr; return nullptr;
} }
String Dictionary::getItem(const String& key) const Optional<String> Dictionary::getItemAsString(const String& key) const
{ {
return (*mStringData.find(key)).value(); if (isString())
{
return mStringVal;
}
return {};
} }
void Dictionary::addStringItem(const String& key, const String& item) bool Dictionary::hasKey(const String& key) const
{ {
mStringData.insert(key, item); return mMapVal.has_key(key);
} }
void Dictionary::addDictItem(const String& key, Ptr<Dictionary> dict) bool Dictionary::isMap() const
{ {
mDictData.insert(key, std::move(dict)); return mType == Type::MAP;
} }
bool Dictionary::isString() const
{
return mType == Type::SCALAR && mScalarType == ScalarType::STRING;
}

View file

@ -1,34 +1,57 @@
#pragma once #pragma once
#include "String.h" #include "String.h"
#include "Number.h"
#include "Vector.h" #include "Vector.h"
#include "Map.h" #include "Map.h"
#include "Pointer.h" #include "Pointer.h"
#include "Optional.h"
class Dictionary class Dictionary
{ {
public: public:
enum class Type
{
MAP,
SEQUENCE,
SCALAR
};
enum class ScalarType
{
STRING,
NUMBER,
BOOLEAN,
NULLT
};
Dictionary() = default; Dictionary() = default;
Dictionary(const String& item);
virtual ~Dictionary() = default; virtual ~Dictionary() = default;
void addStringItem(const String& key, const String& item); void addItem(const String& key, const String& item);
void addDictItem(const String& key, Ptr<Dictionary> dict); void addItem(const String& key, Ptr<Dictionary> dict);
Dictionary* getDict(const String& key) const; Dictionary* getItemAsMap(const String& key) const;
Vector<String> getDictKeys() const; Optional<String> getItemAsString(const String& key) const;
Vector<String> getStringKeys() const; Vector<String> getKeys() const;
String getItem(const String& key) const;
bool hasKey(const String& key) const; bool hasKey(const String& key) const;
bool hasStringKey(const String& key) const; bool isMap() const;
bool hasDictKey(const String& key) const; bool isString() const;
protected: protected:
Map<String, String> mStringData; Type mType{Type::MAP};
Map<String, Ptr<Dictionary> > mDictData; ScalarType mScalarType{ScalarType::STRING};
String mStringVal;
bool mBoolVal{false};
Number mNumberVal;
Vector<Ptr<Dictionary>> mSequenceVal;
Map<String, Ptr<Dictionary> > mMapVal;
}; };

View file

@ -4,6 +4,8 @@ template<typename T, typename U>
class Pair class Pair
{ {
public: public:
Pair() = default;
Pair(const T& t, const U& u) Pair(const T& t, const U& u)
: m_first(t), : m_first(t),
m_second(u) m_second(u)

View file

@ -84,7 +84,6 @@ public:
bool operator!=(const String& other) const; bool operator!=(const String& other) const;
class StringIter class StringIter
{ {
public: public:
@ -143,4 +142,11 @@ private:
Vector<char> m_data; Vector<char> m_data;
}; };
inline String operator+(const char* str, const String& s)
{
String ret(str);
ret += s;
return ret;
}
using _s = String; using _s = String;

View file

@ -5,6 +5,8 @@
#include <errno.h> #include <errno.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <stdio.h>
Status Directory::getDirectoryContents(const FileSystemPath& path, Status Directory::getDirectoryContents(const FileSystemPath& path,
Vector<FileSystemPath>& ret, bool directoryOnly) Vector<FileSystemPath>& ret, bool directoryOnly)
{ {
@ -147,7 +149,6 @@ Status Directory::getFilesWithExtension(const FileSystemPath& path,
Status Directory::create(const FileSystemPath& path, bool existsOk) Status Directory::create(const FileSystemPath& path, bool existsOk)
{ {
(void)existsOk;
FileSystemPath working_path; FileSystemPath working_path;
if (path.is_directory().value()) if (path.is_directory().value())
{ {
@ -158,9 +159,28 @@ Status Directory::create(const FileSystemPath& path, bool existsOk)
working_path = path.parent_path(); working_path = path.parent_path();
} }
if (!working_path.exists()) if (working_path.exists())
{ {
//std::filesystem::create_directories(working_path); if (!existsOk)
{
return Status(Error(
"Attempted to create existing directory."
));
}
return {};
}
else
{
errno = 0;
mode_t mode{S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH};
Status status;
const auto rc = ::mkdir(working_path.str().raw(),
mode);
if (rc !=0)
{
status.on_errno("Failed to create directory.");
}
return status;
} }
return {}; return {};
} }

View file

@ -126,9 +126,22 @@ String FileSystemPath::extension() const
return result; return result;
} }
FileSystemPath FileSystemPath::stem() const
{
const auto split = m_path.rsplit('/');
if (split.second().empty())
{
return split.first();
}
else
{
return split.second();
}
}
String FileSystemPath::file_name() const String FileSystemPath::file_name() const
{ {
String name_and_ext;; String name_and_ext;
const auto split = m_path.rsplit('/'); const auto split = m_path.rsplit('/');
if (split.second().empty()) if (split.second().empty())
{ {

View file

@ -36,6 +36,8 @@ public:
FileSystemPath parent_path() const; FileSystemPath parent_path() const;
FileSystemPath stem() const;
FileSystemPath operator/ (const char* body) const FileSystemPath operator/ (const char* body) const
{ {
String ret = m_path; String ret = m_path;

View file

@ -62,12 +62,7 @@ public:
m_raw = nullptr; m_raw = nullptr;
} }
T* get() T* get() const
{
return m_raw;
}
const T* get() const
{ {
return m_raw; return m_raw;
} }

View file

@ -0,0 +1,15 @@
#pragma once
#include "Dictionary.h"
class JsonDocument
{
public:
const Dictionary& get_data() const
{
return mData;
}
private:
Dictionary mData;
};

View file

@ -0,0 +1,12 @@
#include "JsonParser.h"
Ptr<JsonDocument> JsonParser::read(const FileSystemPath& input_file)
{
return {};
}
Ptr<JsonDocument> JsonParser::read(InputStream<Byte>& stream)
{
return {};
}

View file

@ -0,0 +1,23 @@
#pragma once
#include "FileSystemPath.h"
#include "Stream.h"
#include "JsonDocument.h"
class JsonParser
{
public:
Ptr<JsonDocument> read(const FileSystemPath& input_file);
Ptr<JsonDocument> read(InputStream<Byte>& stream);
private:
enum class State
{
READY,
IN_OBJECT,
IN_ARRAY,
IN_STRING,
IN_NUMBER
};
};

View file

@ -10,7 +10,7 @@ TomlTable::TomlTable(const String& header)
void TomlTable::addComment(const Comment& comment) void TomlTable::addComment(const Comment& comment)
{ {
//mComments.push_back(comment); mComments.push_back(comment);
} }
void TomlTable::addTable(Ptr<TomlTable> table) void TomlTable::addTable(Ptr<TomlTable> table)
@ -28,7 +28,7 @@ String TomlTable::getHeader() const
return mHeader; return mHeader;
} }
const TomlTable* TomlTable::getTable(const String& path) TomlTable* TomlTable::getTable(const String& path) const
{ {
return (*mTables.find(path)).value().get(); return (*mTables.find(path)).value().get();
} }
@ -45,16 +45,14 @@ TomlContent::TomlContent()
} }
const TomlTable* TomlContent::getRootTable() const TomlTable* TomlContent::getRootTable() const
{ {
//return mRootTable.get(); return mRootTable.get();
return nullptr;
} }
const TomlTable* TomlContent::getTable(const String& path) const TomlTable* TomlContent::getTable(const String& path) const
{ {
//return mRootTable->getTable(path); return mRootTable->getTable(path);
return nullptr;
} }
TomlReader::TomlReader() TomlReader::TomlReader()
@ -63,10 +61,9 @@ TomlReader::TomlReader()
} }
const TomlContent* TomlReader::getContent() const TomlContent* TomlReader::getContent() const
{ {
//return mContent.get(); return mContent.get();
return nullptr;
} }
void TomlReader::read(const FileSystemPath& input_path) void TomlReader::read(const FileSystemPath& input_path)
@ -74,7 +71,7 @@ void TomlReader::read(const FileSystemPath& input_path)
Vector<String> lines; Vector<String> lines;
File(input_path).readLines(lines); File(input_path).readLines(lines);
mLastSectionOffset = 0; mLastSectionOffset = 0;
//mWorkingTable = mContent->getRootTable(); mWorkingTable = mContent->getRootTable();
for (const auto& line : lines) for (const auto& line : lines)
{ {

View file

@ -22,7 +22,7 @@ public:
String getHeader() const; String getHeader() const;
const TomlTable* getTable(const String& path); TomlTable* getTable(const String& path) const;
const KeyValuePairs& getKeyValuePairs() const; const KeyValuePairs& getKeyValuePairs() const;
@ -38,9 +38,9 @@ class TomlContent
public: public:
TomlContent(); TomlContent();
const TomlTable* getRootTable() const; TomlTable* getRootTable() const;
const TomlTable* getTable(const String& path) const; TomlTable* getTable(const String& path) const;
private: private:
Ptr<TomlTable> mRootTable; Ptr<TomlTable> mRootTable;
@ -51,7 +51,7 @@ class TomlReader
public: public:
TomlReader(); TomlReader();
const TomlContent* getContent() const; TomlContent* getContent() const;
void read(const FileSystemPath& input_path); void read(const FileSystemPath& input_path);

View file

@ -0,0 +1,6 @@
#pragma once
class YamlDocument
{
};

View file

@ -0,0 +1,11 @@
#pragma once
#include "ByteTypes.h"
#include "Stream.h"
#include "FileSystemPath.h"
class InputFileStream : public InputStream<Byte>
{
public:
};

View file

@ -14,7 +14,15 @@ template<typename T>
class InputStream : public Stream<T> class InputStream : public Stream<T>
{ {
public: public:
virtual Optional<T> get() = 0; Optional<T> get()
{
T item;
if (get(item))
{
return {item};
}
return {};
}
virtual bool get(T& item) = 0; virtual bool get(T& item) = 0;
}; };

View file

@ -1,28 +0,0 @@
set(MODULE_NAME database)
set(SQLite3_INCLUDE_DIR "${CMAKE_SOURCE_DIR}/src/third_party/sqlite3")
set(SQLite3_SOURCE_FILE "${CMAKE_SOURCE_DIR}/src/third_party/sqlite3/sqlite3.c")
list(APPEND HEADERS
Database.h
DatabaseManager.h
database_interfaces/SqliteInterface.h
${SQLite3_SOURCE_FILE})
list(APPEND SOURCES
Database.cpp
DatabaseManager.cpp
database_interfaces/SqliteInterface.cpp
${SQLite3_SOURCE_FILE})
add_library(${MODULE_NAME} SHARED ${SOURCES} ${HEADERS})
target_include_directories(${MODULE_NAME} PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/database_interfaces
${SQLite3_INCLUDE_DIR}
)
target_link_libraries(${MODULE_NAME} core)
set_property(TARGET ${MODULE_NAME} PROPERTY FOLDER src/base)
set_target_properties( ${MODULE_NAME} PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS ON )

View file

@ -0,0 +1,11 @@
#include "Battery.h"
#include "File.h"
String Battery::get_capacity()
{
String content;
File f("/sys/class/power_supply/BAT1/capacity");
f.readText(content);
return content;
}

View file

@ -0,0 +1,10 @@
#pragma once
#include "String.h"
class Battery
{
public:
static String get_capacity();
}

View file

@ -1,72 +0,0 @@
set(MODULE_NAME geometry)
list(APPEND HEADERS
AbstractGeometricItem.h
Bounds.h
Transform.h
Rotation.h
grid/AbstractGrid.h
grid/TypedGrid.h
grid/Grid.h
grid/SparseGrid.h
math/Linalg.h
math/Matrix.h
math/Vector.h
path/Curve.h
path/Line.h
path/LineSegment.h
path/Path.h
path/PathElement.h
path/Arc.h
path/QuadraticBezierCurve.h
path/CubicBezierCurve.h
points/Point.h
points/PointParser.h
points/PointCollection.h
points/DiscretePoint.h
primitives/Circle.h
primitives/Polygon.h
primitives/Rectangle.h
primitives/Triangle.h
)
list(APPEND SOURCES
Rotation.cpp
Bounds.cpp
Transform.cpp
grid/AbstractGrid.cpp
math/Linalg.cpp
math/Matrix.cpp
math/Vector.cpp
path/Curve.cpp
path/Line.cpp
path/LineSegment.cpp
path/Path.cpp
path/PathElement.cpp
path/Arc.cpp
path/QuadraticBezierCurve.cpp
path/CubicBezierCurve.cpp
points/Point.cpp
points/PointParser.cpp
points/PointCollection.cpp
points/DiscretePoint.cpp
primitives/Circle.cpp
primitives/Polygon.cpp
primitives/Rectangle.cpp
primitives/Triangle.cpp
)
add_library(${MODULE_NAME} SHARED ${SOURCES} ${HEADERS})
target_include_directories(${MODULE_NAME} PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/math
${CMAKE_CURRENT_SOURCE_DIR}/path
${CMAKE_CURRENT_SOURCE_DIR}/points
${CMAKE_CURRENT_SOURCE_DIR}/primitives
${CMAKE_CURRENT_SOURCE_DIR}/grid
)
target_link_libraries( ${MODULE_NAME} PUBLIC core)
set_target_properties( ${MODULE_NAME} PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS ON )
set_property(TARGET ${MODULE_NAME} PROPERTY FOLDER src/base)

View file

@ -1,70 +0,0 @@
set(MODULE_NAME network)
set(platform_INCLUDES)
set(platform_LIBS)
if(UNIX)
list(APPEND platform_INCLUDES
sockets/BerkeleySocket.h
sockets/BerkeleySocket.cpp
server/UnixSocketServer.h
server/UnixSocketServer.cpp
client/unix/UnixSocketClient.h
client/unix/UnixSocketClient.cpp
)
else()
list(APPEND platform_INCLUDES
server/win32/Win32WebServer.h
server/win32/Win32WebServer.cpp
server/win32/Win32TempFile.h
server/win32/Win32TempFile.cpp
server/win32/Win32WebRequest.h
server/win32/Win32WebRequest.cpp
server/win32/Win32WebResponse.h
server/win32/Win32WebResponse.cpp
server/win32/Win32Buffer.h
server/win32/Win32Buffer.cpp
server/WinsockServer.h
server/WinsockServer.cpp
client/win32/WinsockClient.h
client/win32/WinsockClient.cpp
sockets/WinsockInterface.h
sockets/WinsockInterface.cpp
sockets/WinsockSocket.h
sockets/WinsockSocket.cpp
)
list(APPEND platform_LIBS Httpapi.lib Ws2_32.lib)
endif()
list(APPEND HEADERS
NetworkManager.h
client/HttpClient.h
client/PlatformSocketClient.h
server/HttpServer.h
server/PlatformSocketServer.h
sockets/Socket.h
sockets/IPlatformSocket.h
)
list(APPEND SOURCES
client/HttpClient.cpp
server/HttpServer.cpp
NetworkManager.cpp
sockets/Socket.cpp
)
add_library(${MODULE_NAME} SHARED ${SOURCES} ${platform_INCLUDES} ${HEADERS})
target_include_directories(${MODULE_NAME} PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/sockets
${CMAKE_CURRENT_SOURCE_DIR}/server
${CMAKE_CURRENT_SOURCE_DIR}/server/win32
${CMAKE_CURRENT_SOURCE_DIR}/client
${CMAKE_CURRENT_SOURCE_DIR}/client/win32
${CMAKE_CURRENT_SOURCE_DIR}/client/unix
)
set_target_properties( ${MODULE_NAME} PROPERTIES WINDOWS_EXPORT_ALL_SYMBOLS ON )
target_link_libraries( ${MODULE_NAME} PUBLIC core ${platform_LIBS})
set_property(TARGET ${MODULE_NAME} PROPERTY FOLDER src/base)