Skip to content

Commit 75c51cf

Browse files
committed
feat: dotNotationToObject improved array support and dynamically create an index with aplha charater to represent the group index [a]
1 parent 59a6382 commit 75c51cf

File tree

1 file changed

+90
-26
lines changed

1 file changed

+90
-26
lines changed

src/index.js

Lines changed: 90 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -100,42 +100,106 @@
100100

101101
function dotNotationToObject(data, obj = {}) {
102102
try {
103+
let arrayGroup = {}; // Track groups by key paths (e.g., 'messages[a]')
104+
103105
for (const key of Object.keys(data)) {
104-
let value = data[key]
105-
let newObject = obj
106-
let oldObject = new Object(obj)
106+
let value = data[key];
107+
let newObject = obj;
108+
let oldObject = new Object(obj);
107109
let keys = key.split('.');
108-
let length = keys.length - 1
110+
let length = keys.length - 1;
111+
109112
for (let i = 0; i < keys.length; i++) {
110-
if (/\[([0-9]*)\]/g.test(keys[i])) {
111-
let [k, index] = keys[i].split('[');
112-
index = index.slice(0, -1) || 0
113-
newObject[k] = oldObject[k] || [];
114-
if (length == i) {
115-
if (value === undefined)
116-
newObject[k].splice(index, 1);
117-
else
118-
newObject[k][index] = value;
119-
} else {
120-
newObject[k][index] = oldObject[k][index] || {};
121-
newObject = newObject[k][index]
122-
oldObject = oldObject[k][index]
113+
// Check if the key ends with ']', indicating an array or grouping operation
114+
if (keys[i].endsWith(']')) {
115+
// Handle array push (e.g., messages[] -> push value)
116+
if (keys[i].endsWith('[]')) {
117+
let baseKey = keys[i].slice(0, -2); // Remove '[]'
118+
119+
// Initialize newObject[baseKey] as an array if not an array or doesn't exist
120+
if (!Array.isArray(newObject[baseKey])) {
121+
newObject[baseKey] = [];
122+
}
123+
124+
if (length == i) {
125+
// If value is an array, spread the array values into newObject[baseKey]
126+
if (Array.isArray(value)) {
127+
newObject[baseKey].push(...value);
128+
} else {
129+
// If value is not an array, just push the single value
130+
newObject[baseKey].push(value);
131+
}
132+
}
123133
}
124-
} else {
134+
// Check for array index (e.g., messages[0])
135+
else if (/\[([0-9]+)\]/g.test(keys[i])) {
136+
let [k, index] = keys[i].split('[');
137+
index = index.slice(0, -1); // Get the index
138+
139+
// Initialize newObject[k] as an array if it doesn't exist or is not an array
140+
if (!Array.isArray(newObject[k])) {
141+
newObject[k] = [];
142+
}
143+
144+
if (length == i) {
145+
if (value === undefined) {
146+
newObject[k].splice(index, 1); // Remove element if value is undefined
147+
} else {
148+
newObject[k][index] = value; // Replace value at specified index
149+
}
150+
} else {
151+
newObject[k][index] = oldObject[k][index] || {}; // Initialize inner object
152+
newObject = newObject[k][index];
153+
oldObject = oldObject[k][index];
154+
}
155+
}
156+
// Handle letter-based groupings (e.g., messages[a].role)
157+
else if (/\[\w\]/g.test(keys[i])) {
158+
let [k, group] = keys[i].split('[');
159+
group = group.slice(0, -1); // Get the letter inside []
160+
161+
// Initialize newObject[k] as an array if not an array or doesn't exist
162+
if (!Array.isArray(newObject[k])) {
163+
newObject[k] = [];
164+
}
165+
166+
// If there's no object at this group index yet, push a new object
167+
let index;
168+
if (arrayGroup[keys.slice(0, i + 1).join('.')]) {
169+
// Reuse the existing index for the group
170+
index = arrayGroup[keys.slice(0, i + 1).join('.')];
171+
} else {
172+
// Create a new group and track the index
173+
index = newObject[k].length;
174+
arrayGroup[keys.slice(0, i + 1).join('.')] = index;
175+
newObject[k][index] = {};
176+
}
177+
178+
// Move into the newly created or existing object for the group
179+
if (length == i) {
180+
newObject[k][index] = value; // Set value in the group
181+
} else {
182+
newObject = newObject[k][index]; // Continue with the group object
183+
}
184+
}
185+
}
186+
// Handle regular object keys (non-array keys)
187+
else {
125188
if (length == i) {
126-
if (value === undefined)
127-
delete newObject[keys[i]]
128-
else
129-
newObject[keys[i]] = value;
189+
if (value === undefined) {
190+
delete newObject[keys[i]]; // Delete key if value is undefined
191+
} else {
192+
newObject[keys[i]] = value; // Set value
193+
}
130194
} else {
131-
newObject[keys[i]] = oldObject[keys[i]] || {};
132-
newObject = newObject[keys[i]]
133-
oldObject = oldObject[keys[i]]
195+
newObject[keys[i]] = oldObject[keys[i]] || {}; // Initialize inner object
196+
newObject = newObject[keys[i]];
197+
oldObject = oldObject[keys[i]];
134198
}
135199
}
136200
}
137201
}
138-
return obj
202+
return obj;
139203
} catch (error) {
140204
console.log("Error converting dot notation to object", error);
141205
return false;

0 commit comments

Comments
 (0)