├── .gitattributes
├── .gitignore
├── CSJsonDB.csproj
├── LICENSE
├── README.md
├── helpers
└── ExtensionMethods.cs
└── src
└── JsonDB.cs
/.gitattributes:
--------------------------------------------------------------------------------
1 | ###############################################################################
2 | # Set default behavior to automatically normalize line endings.
3 | ###############################################################################
4 | * text=auto
5 |
6 | ###############################################################################
7 | # Make sh files under the build directory always have LF as line endings
8 | ###############################################################################
9 | *.sh eol=lf
10 |
11 | ###############################################################################
12 | # Set default behavior for command prompt diff.
13 | #
14 | # This is need for earlier builds of msysgit that does not have it on by
15 | # default for csharp files.
16 | # Note: This is only used by command line
17 | ###############################################################################
18 | #*.cs diff=csharp
19 |
20 | ###############################################################################
21 | # Set the merge driver for project and solution files
22 | #
23 | # Merging from the command prompt will add diff markers to the files if there
24 | # are conflicts (Merging from VS is not affected by the settings below, in VS
25 | # the diff markers are never inserted). Diff markers may cause the following
26 | # file extensions to fail to load in VS. An alternative would be to treat
27 | # these files as binary and thus will always conflict and require user
28 | # intervention with every merge. To do so, just uncomment the entries below
29 | ###############################################################################
30 | #*.sln merge=binary
31 | #*.csproj merge=binary
32 | #*.vbproj merge=binary
33 | #*.vcxproj merge=binary
34 | #*.vcproj merge=binary
35 | #*.dbproj merge=binary
36 | #*.fsproj merge=binary
37 | #*.lsproj merge=binary
38 | #*.wixproj merge=binary
39 | #*.modelproj merge=binary
40 | #*.sqlproj merge=binary
41 | #*.wwaproj merge=binary
42 |
43 | ###############################################################################
44 | # behavior for image files
45 | #
46 | # image files are treated as binary by default.
47 | ###############################################################################
48 | #*.jpg binary
49 | #*.png binary
50 | #*.gif binary
51 |
52 | ###############################################################################
53 | # diff behavior for common document formats
54 | #
55 | # Convert binary document formats to text before diffing them. This feature
56 | # is only available from the command line. Turn it on by uncommenting the
57 | # entries below.
58 | ###############################################################################
59 | #*.doc diff=astextplain
60 | #*.DOC diff=astextplain
61 | #*.docx diff=astextplain
62 | #*.DOCX diff=astextplain
63 | #*.dot diff=astextplain
64 | #*.DOT diff=astextplain
65 | #*.pdf diff=astextplain
66 | #*.PDF diff=astextplain
67 | #*.rtf diff=astextplain
68 | #*.RTF diff=astextplain
69 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Folders
2 | artifacts/
3 | bin/
4 | obj/
5 | .dotnet/
6 | .nuget/
7 | .packages/
8 | .tools/
9 | .vs/
10 | .vscode/
11 | node_modules/
12 | BenchmarkDotNet.Artifacts/
13 | .gradle/
14 | src/SignalR/clients/**/dist/
15 | modules/
16 |
17 | # File extensions
18 | *.aps
19 | *.binlog
20 | *.dll
21 | *.DS_Store
22 | *.exe
23 | *.idb
24 | *.lib
25 | *.log
26 | *.pch
27 | *.pdb
28 | *.pidb
29 | *.psess
30 | *.res
31 | *.snk
32 | *.suo
33 | *.tlog
34 | *.user
35 | *.userprefs
36 | *.vspx
37 |
38 | # Specific files, typically generated by tools
39 | launchSettings.json
40 | msbuild.ProjectImports.zip
41 | StyleCop.Cache
42 | UpgradeLog.htm
43 |
44 | # DocFX site generation (for now)
45 | _site/
--------------------------------------------------------------------------------
/CSJsonDB.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | net5.0
5 | CSJsonDB
6 | 1.1.0
7 | https://github.com/Khelechy/CSJsonDB.git
8 | MIT
9 | git
10 | Kelechi Onyekwere
11 | khelechy
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2021 Onyekwere Kelechi Mark
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # CSJsonDB
2 | ## Introduction
3 |
4 | This is a simple C# package that performs basic CRUD ( Create, Read, Update, Delete ) operations on a Json file, used for sample minimalistic DBs.
5 |
6 | ## Installation
7 |
8 | Install via .NET CLI
9 |
10 | ```bash
11 | dotnet add package CSJsonDB --version 1.1.0
12 | ```
13 | Install via Package Manager
14 |
15 | ```bash
16 | Install-Package CSJsonDB --version 1.1.0
17 | ```
18 |
19 | ### Add the namespace directive `using CSJsonDB;` `IMPORTANT`
20 |
21 | Sample DB `users.db`
22 |
23 | ```json
24 | {
25 | "users": [
26 | {
27 | "id": 1,
28 | "firstname": "kelechi",
29 | "lastname": "onyekwere",
30 | "age": 19,
31 | "verified": true
32 | },
33 | {
34 | "id": 2,
35 | "firstname": "john",
36 | "lastname": "doe",
37 | "age": 33,
38 | "verified": true
39 | },
40 | {
41 | "id": 3,
42 | "firstname": "mark",
43 | "lastname": "parker",
44 | "age": 20,
45 | "verified": false
46 | }
47 | ]
48 | }
49 | ```
50 |
51 | ### Load the Sample DB `IMPORTANT`
52 |
53 | ```c#
54 | var db = JsonDB.Load("filepathtosampledb/users.db");
55 | ```
56 |
57 | ## Available Methods 🧨
58 |
59 | >**NOTE**
60 | >Responses are returned as objects. You can use `.ToJsonString()` method to return json string from a json object
61 |
62 | ### Load
63 |
64 | ```c#
65 | var db = JsonDB.Load(string filePath);
66 | ```
67 |
68 |
69 | ### ToJsonString
70 |
71 | ```c#
72 | db.Select("users").Where("id", 2).ToJsonString();
73 | ```
74 | result: `string` Returns the json string of the object.
75 |
76 | ### Select
77 |
78 | ```c#
79 | db.Select(string table);
80 | ```
81 |
82 | #### Sample
83 | ```c#
84 | db.Select("users");
85 | ```
86 | result: `object`
87 | ```json
88 | [
89 | {
90 | "id": 1,
91 | "firstname": "kelechi",
92 | "lastname": "onyekwere",
93 | "age": 19,
94 | "verified": true
95 | },
96 | {
97 | "id": 2,
98 | "firstname": "john",
99 | "lastname": "doe",
100 | "age": 33,
101 | "verified": true
102 | },
103 | {
104 | "id": 3,
105 | "firstname": "mark",
106 | "lastname": "parker",
107 | "age": 20,
108 | "verified": false
109 | }
110 | ]
111 | ```
112 |
113 | ### Where
114 | ```c#
115 | db.Select(string table).Where(string key, dynamic value);
116 | ```
117 | #### Sample
118 | ```c#
119 | db.Select("users").Where("id", 2);
120 | ```
121 | result: `List`
122 | ```json
123 | [
124 | {
125 | "id": 2,
126 | "firstname": "john",
127 | "lastname": "doe",
128 | "age": 33,
129 | "verified": true
130 | },
131 | ]
132 | ```
133 |
134 | ### Add
135 | ```c#
136 | db.Add(string table, object newData);
137 | ```
138 | #### Sample
139 | ```c#
140 | var newUser = new {
141 | id = 3,
142 | firstname = matt,
143 | lastname = doe,
144 | age = 23,
145 | verified = false
146 | };
147 |
148 | db.Add("users", newUser);
149 | ```
150 | result: void
151 |
152 | ### Delete
153 | ```c#
154 | db.Delete(string table, string key, dynamic value);
155 | ```
156 | #### Sample
157 | ```c#
158 | db.Delete("users", "id", 1);
159 | ```
160 | result: void
161 |
162 | ### Update
163 | ```c#
164 | db.Update(string table, string key, dynamic value, object newData);
165 | ```
166 | #### Sample
167 | ```c#
168 | var updateUser = new {
169 | verified = true
170 | };
171 |
172 | db.Update("users", "id", 3, updateUser);
173 | ```
174 | result: `object`
175 | ```json
176 | [
177 | {
178 | "id": 3,
179 | "firstname": "mark",
180 | "lastname": "parker",
181 | "age": 20,
182 | "verified": true
183 | },
184 | ]
185 | ```
186 |
187 |
188 | ## Contribution
189 |
190 | If you find an issue with this package or you have any suggestion please help out. I am not perfect.
191 |
--------------------------------------------------------------------------------
/helpers/ExtensionMethods.cs:
--------------------------------------------------------------------------------
1 | using Newtonsoft.Json.Linq;
2 | using System;
3 | using System.Collections.Generic;
4 | using System.Linq;
5 | using System.Text;
6 | using System.Threading.Tasks;
7 |
8 | namespace CSJsonDB.helpers
9 | {
10 | public static class ExtensionMethods
11 | {
12 | public static JArray ToDataList(this object data)
13 | {
14 | if (data != null)
15 | {
16 | try
17 | {
18 | var token = JToken.Parse(data.ToString());
19 | if (token is JArray)
20 | {
21 |
22 | JArray dataArray = (JArray)data;
23 | return dataArray;
24 | }
25 | else
26 | {
27 | throw new Exception("The preloaded data is not a Json Array");
28 | }
29 | }
30 | catch (Exception ex)
31 | {
32 | throw new Exception(ex.Message.ToString());
33 | }
34 | }
35 | else
36 | {
37 | throw new Exception("The preloaded data is null");
38 | }
39 | }
40 |
41 | }
42 | }
43 |
--------------------------------------------------------------------------------
/src/JsonDB.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.IO;
3 | using System.Linq;
4 | using Newtonsoft.Json;
5 | using Newtonsoft.Json.Linq;
6 | using System.Collections.Generic;
7 | using System.Reflection;
8 | using CSJsonDB.helpers;
9 |
10 | namespace CSJsonDB
11 | {
12 | public static class JsonDB
13 | {
14 | public static string jsonFile;
15 | public static string jsonLocation;
16 | private static JObject _dbObject;
17 |
18 | public static JObject Load(string filePathLoaded)
19 | {
20 | if (!File.Exists(filePathLoaded))
21 | throw new Exception("File does not exist, please check file or file path");
22 | try
23 | {
24 | jsonFile = File.ReadAllText(filePathLoaded);
25 | jsonLocation = filePathLoaded;
26 | return _dbObject = JObject.Parse(jsonFile);
27 | }
28 | catch (Exception ex)
29 | {
30 | throw new Exception(ex.Message.ToString());
31 | }
32 | }
33 |
34 | public static object Select(this object data, string table = "")
35 | {
36 |
37 | if (data != null)
38 | {
39 | try
40 | {
41 | var parsedData = JObject.Parse(data.ToString());
42 | var result = string.IsNullOrEmpty(table) ? (object)parsedData : (object)parsedData[table];
43 | return result;
44 | }
45 | catch (Exception ex)
46 | {
47 | throw new Exception(ex.Message.ToString());
48 | }
49 | }
50 | else
51 | {
52 | throw new Exception("The preloaded data is null");
53 | }
54 | }
55 |
56 | public static List Where(this object data, string key = "", dynamic value = null)
57 | {
58 | if (data != null)
59 | {
60 | var dataArray = data.ToDataList();
61 | var newDataArray = new List();
62 | foreach (var singleData in dataArray.Where(x => x[key] as dynamic == value))
63 | {
64 | newDataArray.Add(singleData);
65 | }
66 | return newDataArray;
67 | }
68 | else
69 | {
70 | throw new Exception("The preloaded data is null");
71 | }
72 |
73 | }
74 |
75 | public static void Add(this object data, string table, object newData)
76 | {
77 | if (data != null)
78 | {
79 | try
80 | {
81 | var parsedData = JObject.Parse(data.ToString());
82 | var result = string.IsNullOrEmpty(table) ? (object)parsedData : (object)parsedData[table];
83 | var dataArray = result.ToDataList();
84 | dataArray.Add(JObject.Parse(JsonConvert.SerializeObject(newData, Formatting.Indented)));
85 | parsedData[table] = dataArray;
86 | string newJsonResult = parsedData.ToString();
87 | File.WriteAllText(jsonLocation, newJsonResult);
88 | }
89 | catch (Exception ex)
90 | {
91 | throw new Exception(ex.Message.ToString());
92 | }
93 | }
94 | else
95 | {
96 | throw new Exception("The preloaded data is null");
97 | }
98 | }
99 |
100 | public static void Delete(this object data, string table, string key, dynamic value)
101 | {
102 | if (data != null)
103 | {
104 | try
105 | {
106 | var parsedData = JObject.Parse(data.ToString());
107 | var result = (object)parsedData[table];
108 | var dataArray = result.ToDataList();
109 | var itemToBeDeleted = dataArray.FirstOrDefault(x => x[key] as dynamic == value);
110 | if (itemToBeDeleted == null)
111 | throw new Exception("There are no objects with key: " + key + " , Please check key again");
112 | dataArray.Remove(itemToBeDeleted);
113 | parsedData[table] = dataArray;
114 | string newJsonResult = parsedData.ToString();
115 | File.WriteAllText(jsonLocation, newJsonResult);
116 | }
117 | catch (Exception ex)
118 | {
119 | throw new Exception(ex.Message.ToString());
120 | }
121 | }
122 | else
123 | {
124 | throw new Exception("The preloaded data is null");
125 | }
126 | }
127 |
128 | public static object Update(this object data, string table, string key, dynamic value, object newData)
129 | {
130 | if (data != null)
131 | {
132 | try
133 | {
134 | var parsedData = JObject.Parse(data.ToString());
135 | var result = (object)parsedData[table];
136 | var dataArray = result.ToDataList();
137 | var x = dataArray.FirstOrDefault(x => x[key] as dynamic == value);
138 | if (x == null)
139 | throw new Exception("There are no objects with key: " + key + " , Please check key again");
140 | foreach (PropertyInfo prop in newData.GetType().GetProperties())
141 | {
142 | var valueObject = prop.GetValue(newData, null);
143 | x[prop.Name] = JToken.FromObject(valueObject);
144 | }
145 | parsedData[table] = dataArray;
146 | string newJsonResult = parsedData.ToString();
147 | File.WriteAllText(jsonLocation, newJsonResult);
148 | return x;
149 | }
150 | catch (Exception ex)
151 | {
152 | throw new Exception(ex.Message.ToString());
153 | }
154 | }
155 | else
156 | {
157 | throw new Exception("The preloaded data is null");
158 | }
159 | }
160 |
161 | public static string ToJsonString(this object data)
162 | {
163 | if(data != null)
164 | {
165 | return JsonConvert.SerializeObject(data);
166 | }
167 | else
168 | {
169 | throw new Exception("The preloaded data is null");
170 | }
171 | }
172 |
173 | ///
174 | /// Gets the next available ID for a specified table and ID field
175 | ///
176 | /// The table name to search
177 | /// The ID field name (default: "id")
178 | /// The next available ID
179 | public static int GetNextId(string table, string idField = "id")
180 | {
181 | if (_dbObject == null)
182 | throw new Exception("Database not loaded. Call Load() first.");
183 |
184 | var tableArray = _dbObject[table] as JArray;
185 | if (tableArray == null)
186 | return 1; // Return 1 if table doesn't exist or is empty
187 |
188 | int maxId = 0;
189 |
190 | foreach (var item in tableArray)
191 | {
192 | if (item[idField] != null && item[idField].Type == JTokenType.Integer)
193 | {
194 | int currentId = item[idField].Value();
195 | if (currentId > maxId)
196 | maxId = currentId;
197 | }
198 | }
199 |
200 | return maxId + 1;
201 | }
202 | }
203 | }
204 |
--------------------------------------------------------------------------------