0

I have a situation where I need to filter an array of objects based on certain conditions. And here what it is

  • There is an error response and the response is an array of objects. Each object has nodes message, type, keyValues
  • keyValues is an array and may have 3 different items at-most. The nodes for each element are key & value
  • key can have one of the following 3 values by-date , by-unique-object, by-related-object
  • value for by-date will have the value as date object
  • value for by-unique-object, by-related-object will have object as

    value: {
       uri: "object-uri-1"
    }

  • The uri has specific pattern and same for both of the types by-unique-object, by-related-object.

So, from the given error array I need to filter only the records which got only by-date and should not have other 2 types with those types of URI pattern

Here what I did -

let errors = [
    {
        message: "Error message 1",
        type: "error",
        keyValues: [
            {
                key: "by-date",
                value: {
                    date: {year:2020, month: 4, day: 6}
                }
            },
            {
                key: "by-unique-object",
                value: {
                    uri: "object-uri-1"
                }
            },
            {
                key: "by-related-object",
                value: {
                    uri: "object-uri-1"
                }
            },
        ]
    },
    {
        message: "Error message 2",
        type: "error",
        keyValues: [
            {
                key: "by-date",
                value: {
                    date: {year:2020, month: 4, day: 5}
                }
            }
        ]
    },
    {
        message: "Error message 3",
        type: "error",
        keyValues: [
            {
                key: "by-date",
                value: {
                    date: {year:2020, month: 4, day: 6}
                }
            },
            {
                key: "by-unique-object",
                value: {
                    uri: "object-uri-3"
                }
            }
        ]
    },
    {
        message: "Error message 4",
        type: "warning",
        keyValues: [
            {
                key: "by-unique-object",
                value: {
                    uri: "object-uri-4"
                }
            },
            {
                key: "by-related-object",
                value: {
                    uri: "object-uri-4"
                }
            }
        ]
    },
    {
        message: "Error message 5",
        type: "warning",
        keyValues: [
            {
                key: "by-date",
                value: {
                    date: {year:2020, month: 4, day: 8}
                }
            },
            {
                key: "by-related-object",
                value: {
                    uri: "object-uri-4"
                }
            }
        ]
    },
    {
        message: "Error message 6",
        type: "warning",
        keyValues: [
            {
                key: "by-date",
                value: {
                    date: {year:2020, month: 4, day: 9}
                }
            }
        ]
    }
];
const matchObjectUriPattern = (uri) => /object-uri-.*/g.test(uri);
const hasByDate = (item) => item.key === "by-date" && item.value && item.value.date;
const hasUniqueObject = (item) => item.key === "by-unique-object" && matchObjectUriPattern(item.value.uri);
const hasRelatedObject = (item) => item.key === "by-related-object" && matchObjectUriPattern(item.value.uri);


const checkOnlyByDate = (error) => {
    let keyValues = error && error.keyValues ? error.keyValues : [];
    let byDate = keyValues.find(hasByDate);
    let byUniqueObject = keyValues.find(hasUniqueObject);
    let byRelatedObject = keyValues.find(hasRelatedObject);

    return byDate && (!byUniqueObject && !byRelatedObject);
};

const filteredErrors = errors.filter(checkOnlyByDate);

console.log(JSON.stringify(filteredErrors)); 

What I did works well, but is there a better way to do it ? Or some better way to handle this ?

1 Answer 1

1

I like your solution! Based on your requirements I came up with:

const filteredErrors = errors.filter(({keyValues}) => 
  keyValues.every(({key}) => key === "by-date"))

Which only returns those error messages whose keyValues array only contains objects with key === "by-date"

I can't say this is better or worse than what you provided because I'm not sure how else you might be using this code. But I wanted to add my own interpretation of the problem.

Sign up to request clarification or add additional context in comments.

1 Comment

Interesting I completely missed that Array.prototype.every() is meant to do such job !! I ended up having so much of code. This is what I wanted less code but super effective. Thanks and stay safe in this difficult covid19 situation !!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.