KiCad PCB EDA Suite
Loading...
Searching...
No Matches
nested_settings.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright (C) 2020 Jon Evans <[email protected]>
5 * Copyright (C) 2020, 2023 KiCad Developers, see AUTHORS.txt for contributors.
6 *
7 * This program is free software: you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License as published by the
9 * Free Software Foundation, either version 3 of the License, or (at your
10 * option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License along
18 * with this program. If not, see <http://www.gnu.org/licenses/>.
19 */
20
21#include <wx/log.h>
22
25#include <locale_io.h>
26
27
28NESTED_SETTINGS::NESTED_SETTINGS( const std::string& aName, int aVersion, JSON_SETTINGS* aParent,
29 const std::string& aPath, bool aLoadFromFile ) :
30 JSON_SETTINGS( aName, SETTINGS_LOC::NESTED, aVersion ),
31 m_parent( aParent ), m_path( aPath )
32{
33 SetParent( aParent, aLoadFromFile );
34}
35
36
38{
39 if( m_parent )
41}
42
43
44bool NESTED_SETTINGS::LoadFromFile( const wxString& aDirectory )
45{
46 m_internals->clear();
47 bool success = false;
48
49 if( m_parent )
50 {
51 nlohmann::json::json_pointer ptr = m_internals->PointerFromString( m_path );
52
53 if( m_parent->m_internals->contains( ptr ) )
54 {
55 try
56 {
57 m_internals->update( m_parent->m_internals->at( ptr ) );
58
59 wxLogTrace( traceSettings, wxT( "Loaded NESTED_SETTINGS %s" ), GetFilename() );
60
61 success = true;
62 }
63 catch( ... )
64 {
65 wxLogTrace( traceSettings, wxT( "NESTED_SETTINGS %s: Could not load from "
66 "%s at %s" ),
68 }
69 }
70 }
71
72 if( success )
73 {
74 int filever = -1;
75
76 try
77 {
78 filever = m_internals->Get<int>( "meta.version" );
79 }
80 catch( ... )
81 {
82 wxLogTrace( traceSettings, wxT( "%s: nested settings version could not be read!" ),
83 m_filename );
84 success = false;
85 }
86
87 if( filever >= 0 && filever < m_schemaVersion )
88 {
89 wxLogTrace( traceSettings, wxT( "%s: attempting migration from version %d to %d" ),
90 m_filename, filever, m_schemaVersion );
91
92 bool migrated = false;
93
94 try
95 {
96 migrated = Migrate();
97 }
98 catch( ... )
99 {
100 success = false;
101 }
102
103 if( !migrated )
104 {
105 wxLogTrace( traceSettings, wxT( "%s: migration failed!" ), GetFullFilename() );
106 success = false;
107 }
108 }
109 else if( filever > m_schemaVersion )
110 {
111 wxLogTrace( traceSettings,
112 wxT( "%s: warning: nested settings version %d is newer than latest (%d)" ),
113 m_filename, filever, m_schemaVersion );
114 }
115 else if( filever >= 0 )
116 {
117 wxLogTrace( traceSettings, wxT( "%s: schema version %d is current" ),
118 m_filename, filever );
119 }
120 }
121
122 Load();
123
124 return success;
125}
126
127
128bool NESTED_SETTINGS::SaveToFile( const wxString& aDirectory, bool aForce )
129{
130 if( !m_parent )
131 return false;
132
134
135 try
136 {
137 bool modified = Store();
138
139 auto jsonObjectInParent = m_parent->GetJson( m_path );
140
141 if( !jsonObjectInParent )
142 modified = true;
143 else if( !nlohmann::json::diff( *m_internals, jsonObjectInParent.value() ).empty() )
144 modified = true;
145
146 if( modified || aForce )
147 {
148 ( *m_parent->m_internals )[m_path].update( *m_internals );
149
150 wxLogTrace( traceSettings, wxS( "Stored NESTED_SETTINGS %s with schema %d" ),
151 GetFilename(),
153 }
154
155 return modified;
156 }
157 catch( ... )
158 {
159 wxLogTrace( traceSettings, wxS( "NESTED_SETTINGS %s: Could not store to %s at %s" ),
162 m_path );
163
164 return false;
165 }
166}
167
168
169void NESTED_SETTINGS::SetParent( JSON_SETTINGS* aParent, bool aLoadFromFile )
170{
171 m_parent = aParent;
172
173 if( m_parent )
174 {
176
177 // In case we were created after the parent's ctor
178 if( aLoadFromFile )
179 LoadFromFile();
180 }
181}
std::optional< nlohmann::json > GetJson(const std::string &aPath) const
Fetches a JSON object that is a subset of this JSON_SETTINGS object, using a path of the form "key1....
wxString m_filename
The filename (not including path) of this settings file (inicode)
virtual void Load()
Updates the parameters of this object based on the current JSON document contents.
wxString GetFullFilename() const
bool Migrate()
Migrates the schema of this settings from the version in the file to the latest version.
void ReleaseNestedSettings(NESTED_SETTINGS *aSettings)
Saves and frees a nested settings object, if it exists within this one.
std::unique_ptr< JSON_SETTINGS_INTERNALS > m_internals
friend class NESTED_SETTINGS
Definition: json_settings.h:69
int m_schemaVersion
Version of this settings schema.
void AddNestedSettings(NESTED_SETTINGS *aSettings)
Transfers ownership of a given NESTED_SETTINGS to this object.
virtual bool Store()
Stores the current parameters into the JSON document represented by this object Note: this doesn't do...
wxString GetFilename() const
Definition: json_settings.h:80
Instantiate the current locale within a scope in which you are expecting exceptions to be thrown.
Definition: locale_io.h:49
void SetParent(JSON_SETTINGS *aParent, bool aLoadFromFile=true)
std::string m_path
The path (in pointer format) of where to store this document in the parent.
JSON_SETTINGS * m_parent
A pointer to the parent object to load and store from.
virtual ~NESTED_SETTINGS()
bool SaveToFile(const wxString &aDirectory="", bool aForce=false) override
Calls Store() and then saves the JSON document contents into the parent JSON_SETTINGS.
bool LoadFromFile(const wxString &aDirectory="") override
Loads the JSON document from the parent and then calls Load()
SETTINGS_LOC
Definition: json_settings.h:54
@ NESTED
Not stored in a file, but inside another JSON_SETTINGS.
#define traceSettings
Definition: json_settings.h:52
std::vector< FAB_LAYER_COLOR > dummy