Categories
JavaScript Answers

How to Add Conditional Form Field Validation in Yup?

We can validate a field conditionality with Yup by using the when method.

For instance, we can write:

validationSchema={yup.object().shape({
  showName: yup.boolean(),
  name: yup
    .string()
    .when("showName", {
      is: true,
      then: yup.string().required("name is required")
    })
  })
}

We have the showName boolean field.

And we only validate the name field when it’s true as indicated in the is field.

then lets us do the validation only when showName is true .

Then we return the 'name is required' message if it is.

Categories
JavaScript Answers

How to Map Over a JavaScript Object While Preserving the Keys?

We can use the Lodash mapValues method to map property values of a JavaScript object to new values.

For instance, we can write:

const mapped = _.mapValues({
  one: 1,
  two: 2,
  three: 3
}, (v) => {
  return v * 3;
});
console.log(mapped)

We pass in the object we want to transform the property values for as the first argument.

Then we pass in a function to return the mapped value given the property value v ,

Therefore, mapped is:

{one: 3, two: 6, three: 9}

Use the Object.entries and Object.assign Methods

We can use the Object.entries method to get the key-value pairs of an object as an array.

Then we can call map to maps the key-value pair to what we want.

And then we can use Object.assign to create a new object from the key-value pairs.

For instance, we can write:

const obj = {
  one: 1,
  two: 2,
  three: 3
}
const props = Object.entries(obj).map(([k, v]) => ({
  [k]: v * 3
}))
const mapped = Object.assign(...props);
console.log(mapped)

We call Object.entries with obj .

Then we call map to map the v property value to their new values and return an array of objects each with their own key-value pair with the mapped property value.

Next, we spread the props into Object.assign with the props array spread into Object.assign as arguments.

Therefore, mapped is the same as the previous example.

Categories
JavaScript Answers

How to Join JavaScript Strings with a Delimiter Only if the Strings are not Null or Empty?

We can use the JavaScript array filter method to filter out all the null or empty strings first before joining them together with join .

For instance, we can write:

const address = "foo";
const city = '';
const state = "bar";
const zip = '';

const text = [address, city, state, zip].filter(Boolean).join(", ");
console.log(text)

We have an array of strings with some having empty strings as their value.

So we just call filter with Boolean to filter out the ones with an empty string as their value.

And then we call join to join the non-empty strings together with a comma.

Therefore, text is 'foo, bar’ .

We can also be more precise with our filtering by writing:

const address = "foo";
const city = '';
const state = "bar";
const zip = '';

const text = [address, city, state, zip]
  .filter(x => typeof x === 'string' && x.length > 0)
  .join(", ");
console.log(text)

We check if x is a string and if its length is longer than 0 to make sure filter returns array of non-empty strings.

Conclusion

We can use the JavaScript array filter method to filter out all the null or empty strings first before joining them together with join .

Categories
JavaScript Answers

How to Define an HTML Template and Append it Using JQuery?

We can use the jQuery append method with a script tag that has its type set to a non-recognized type to add a template.

To do this, we can write:

<script id="hidden-template" type="text/x-custom-template">
  <tr>
   <td>Foo</td>
    <td>Bar</td>
  <tr>
</script>

<table id='targetTable'>

</table>

Then we can write:

const template = $('#hidden-template').html();
$('#targetTable').append(template);

to add the HTML in the script tag into the table element.

Since the type is set to text/x-custom-template which isn’t recognized by the browser, it won’t be parsed by it.

We get the HTML content of the script tag with the html method.

Then we can use append to append the HTML content.

Template String

Another way to add HTML to the DOM is to use template strings.

For instance, we can write:

<div class='list-items'>

</div>

Then we write:

const Item = ({ url, img, title }) => `
  <a href="${url}" class="list-group-item">
    <div class="image">
      <img src="${img}" />
    </div>
    <p class="list-group-item-text">${title}</p>
  </a>
`;
$('.list-items').html([
  { url: '/foo', img: 'https://i.picsum.photos/id/1/200/300.jpg?hmac=jH5bDkLr6Tgy3oAg5khKCHeunZMHq0ehBZr6vGifPLY', title: 'Foo item' },
  { url: '/bar', img: 'https://i.picsum.photos/id/1/200/300.jpg?hmac=jH5bDkLr6Tgy3oAg5khKCHeunZMHq0ehBZr6vGifPLY', title: 'Bar item' },
].map(Item).join(''));

We have the Item function that takes an object with the url , img , and title properties and put them into the template string that it returns.

Then we get the div with $(‘.list-items’) , and then call html with an array objects and map them to strings with a elements by calling map with Item .

And then we call join to join them strings together.

Now we see the items displayed on the page.

Categories
JavaScript Answers

How to Remove a File from a JavaScript FileList?

Use the Spread Operator

One way to remove a file from a JavaScript FileList is to use the spread operator to convert the FileList to an array.

Then we can call splice to remove the file we want.

For instance, we can write the following HTML:

<input type='file' multiple id='files'>

We add multiple to let select multiple files.

Then we can remove one of the items selected by writing:

const input = document.getElementById('files')
input.addEventListener('change', () => {
  const fileListArr = [...input.files]
  fileListArr.splice(1, 1)
  console.log(fileListArr)
})

We get the file input element with getElementById .

We spread input.files into an array.

Then we call splice on the array with index 1 as the first argument and we specify that we remove 1 item with the 2nd arguemnt.

Therefore, fileListArr has the 1st and 3rd file listed.

Use the Array.from Method

We can replace the spread operator with the Array.from method.

For instance, we can write:

<input type='file' multiple id='files'>

And:

const input = document.getElementById('files')
input.addEventListener('change', () => {
  const fileListArr = Array.from(input.files)
  fileListArr.splice(1, 1)
  console.log(fileListArr)
})

to do the same thing.

The only difference is that the spread operator is replaced with Array.from .