Repository: dynamoosejs/dynamoose
Pull request #780 (2020-04-06 13:29:19)

fix(regex): allows attributes to have numeric characters
### Summary:

Allows attributes to have numeric characters

### Other information:

Updated the regex to match dot + number instead of just number.


### Type (select 1):
- [x] Bug fix
- [ ] Feature implementation
- [ ] Documentation improvement
- [ ] Testing improvement
- [ ] Test added to report bug (GitHub issue #--- @---)
- [ ] Something not listed here


### Is this a breaking change? (select 1):
- [ ] 🚨 YES 🚨
- [x] No
- [ ] I'm not sure


### Is this ready to be merged into Dynamoose? (select 1):
- [x] Yes
- [ ] No


### Are all the tests currently passing on this PR? (select 1):
- [x] Yes
- [ ] No


### Other:
- [x] I have searched through the GitHub pull requests to ensure this PR has not already been submitted
- [x] I have updated the Dynamoose documentation (if required) given the changes I made
- [x] I have added/updated the Dynamoose test cases (if required) given the changes I made
- [x] I have ensured the following commands are successful from the root of the project directory
  - [x] `npm test`
  - [x] `npm run lint`
- [x] I agree that all changes made in this pull request may be distributed and are made available in accordance with the [Dynamoose license](https://github.com/dynamoosejs/dynamoose/blob/master/LICENSE)
- [x] All of my commits and commit messages are detailed, explain what changes were made, and are easy to follow and understand
- [x] I have filled out all fields above



Patch:
diff --git a/lib/Document.js b/lib/Document.js
index 8559ec45..088aa235 100644
--- a/lib/Document.js
+++ b/lib/Document.js
@@ -146,7 +146,7 @@ function DocumentCarrier(model) {
 			if (validParents.find((parent) => key.startsWith(parent.key) && (parent.infinite || key.split(".").length === parent.key.split(".").length + 1))) {
 				return;
 			}
-			const genericKey = key.replace(/\d+/gu, "0"); // This is a key replacing all list numbers with 0 to standardize things like checking if it exists in the schema
+			const genericKey = key.replace(/\.\d+/gu, ".0"); // This is a key replacing all list numbers with 0 to standardize things like checking if it exists in the schema
 			const existsInSchema = schemaAttributes.includes(genericKey);
 			if (existsInSchema) {
 				const {isValidType, typeDetails} = getValueTypeCheckResult(value, genericKey, {"standardKey": true});
diff --git a/lib/Schema.js b/lib/Schema.js
index 1d267540..14dabc60 100644
--- a/lib/Schema.js
+++ b/lib/Schema.js
@@ -168,7 +168,7 @@ Schema.prototype.attributes = function() {
 };
 
 Schema.prototype.getAttributeValue = function(key, settings = {}) {
-	return (settings.standardKey ? key : key.replace(/\d+/gu, "0")).split(".").reduce((result, part) => utils.object.get(result.schema, part), {"schema": this.schemaObject});
+	return (settings.standardKey ? key : key.replace(/\.\d+/gu, ".0")).split(".").reduce((result, part) => utils.object.get(result.schema, part), {"schema": this.schemaObject});
 };
 
 class DynamoDBType {
@@ -276,7 +276,7 @@ function retrieveTypeInfo(type, isSet, key, typeSettings) {
 	return isSet ? parentType.set : parentType;
 }
 Schema.prototype.getAttributeTypeDetails = function(key, settings = {}) {
-	const standardKey = (settings.standardKey ? key : key.replace(/\d+/gu, "0"));
+	const standardKey = (settings.standardKey ? key : key.replace(/\.\d+/gu, ".0"));
 	if (this[internalCache].getAttributeTypeDetails[standardKey]) {
 		return this[internalCache].getAttributeTypeDetails[standardKey];
 	}


Test patch:
diff --git a/test/Schema.js b/test/Schema.js
index cb42ccfb..9e55dc1b 100644
--- a/test/Schema.js
+++ b/test/Schema.js
@@ -777,6 +777,12 @@ describe("Schema", () => {
 			expect(func).to.throw("Invalid Attribute: random");
 		});
 
+		it("Should not throw for attribute with number in it (without . prefix)", () => {
+			const func = () => new Schema({"id": String, "ran2dom": String}).getAttributeTypeDetails("ran2dom");
+			expect(func).to.not.throw(Error.UnknownAttribute);
+			expect(func).to.not.throw("Invalid Attribute: ran2dom");
+		});		
+
 		it("Should have correct custom type for date", () => {
 			const functions = new Schema({"id": Date}).getAttributeTypeDetails("id").customType.functions;
 			expect(functions.toDynamo).to.exist;