Repository: jquense/yup
Pull request #171 (2018-02-06 18:01:38)

Added notRequired method to mixed type
Added `notRequired` method so the field can be set as not required.

I have a big form on my project and there are fields that are shown if other fields are equal to something. Applying `.required()` to everyting and then using `.notRequired()` in `.when()` method would be simpler than checking if field depends on other field and if so using different `mixed()` types in `.when()` sections.

For example, I have to use:

```javascript
yup.mixed().when('some-field', {
    is: true,
    then: yup.mixed().required(),  
    otherwise: yup.mixed(),  
});
```

Instead of:

```javascript
const mixedType = yup.mixed().required();

mixedType.when('some-field', {
    is: true,
    then: mixedType,
    otherwise: mixedType.notRequired(),
});
```

Keep in mind that `mixedType` can be a lot more complicated and creating a new type from scratch will cause code duplicating.


Patch:
diff --git a/README.md b/README.md
index 15b163f..6e89b79 100644
--- a/README.md
+++ b/README.md
@@ -47,6 +47,7 @@ json separate from validating it, via the `cast` method.
     - [`mixed.default(): Any`](#mixeddefault-any)
     - [`mixed.nullable(isNullable: boolean = false): Schema`](#mixednullableisnullable-boolean--false-schema)
     - [`mixed.required(message: ?string): Schema`](#mixedrequiredmessage-string-schema)
+    - [`mixed.notRequired(): Schema`](#mixednotrequired-schema)
     - [`mixed.typeError(message: string): Schema`](#mixedtypeerrormessage-string-schema)
     - [`mixed.oneOf(arrayOfValues: Array<any>, string: ?message): Schema` Alias: `equals`](#mixedoneofarrayofvalues-arrayany-string-message-schema-alias-equals)
     - [`mixed.notOneOf(arrayOfValues: Array<any>, string: ?message)`](#mixednotoneofarrayofvalues-arrayany-string-message)
@@ -509,6 +510,10 @@ Indicates that `null` is a valid value for the schema. Without `nullable()`
 
 Mark the schema as required. All field values apart from `undefined` meet this requirement.
 
+#### `mixed.notRequired(): Schema`
+
+Mark the schema as not required. Passing `undefined` as value will not fail validation.
+
 #### `mixed.typeError(message: string): Schema`
 
 Define an error message for failed type checks. The `${value}` and `${type}` interpolation can
diff --git a/src/mixed.js b/src/mixed.js
index 3ffa7ff..96041ea 100644
--- a/src/mixed.js
+++ b/src/mixed.js
@@ -314,6 +314,12 @@ SchemaType.prototype = {
     )
   },
 
+  notRequired() {
+    var next = this.clone()
+    next.tests = next.tests.filter(test => test.TEST_NAME !== 'required')
+    return next
+  },
+
   nullable(value) {
     var next = this.clone()
     next._nullable = value === false ? false : true


Test patch:
diff --git a/test/mixed.js b/test/mixed.js
index 93dc9f1..ae96e17 100644
--- a/test/mixed.js
+++ b/test/mixed.js
@@ -101,6 +101,21 @@ describe('Mixed Types ', () => {
     err.errors[0].should.equal('this must be one of the following values: 5, hello')
   })
 
+  it('should not require field when notRequired was set', async () => {
+    let inst = mixed().required();
+
+    await inst.isValid('test').should.eventually().equal(true)
+    await inst.isValid(1).should.eventually.equal(true)
+
+    let err = await inst.validate().should.be.rejected()
+
+    err.errors[0].should.equal('this is a required field')
+
+    inst = inst.notRequired()
+
+    await inst.isValid().should.eventually.equal(true)
+  })
+
   global.YUP_USE_SYNC &&
     describe('synchronous methods', () => {
       it('should validate synchronously', async () => {