AG Grid: Better way for validation row - valueSetter?
Asked Answered
P

3

1

Is there a better way to validate a row in ag-grid than with valueSetter?

I can achieve the validation with that but I am not sure, if there is a better way.

https://www.ag-grid.com/javascript-grid-value-setters/#properties-for-setters-and-parsers

I want to validate two fields in the row. DateFrom and DateUntil (they are not allow to be null and DateFrom must be lower than DateUntil).

Perdu answered 8/10, 2018 at 21:27 Comment(0)
A
7

There are two ways of possible validation handling:

First: via ValueSetter function

and

Second: via custom cellEditor component

I suggest that it would be better to split the logic between custom components, but as you said you need to validate two cell-values between themselves.

On this case from UI perspective you could try to combine them inside one cell and it would be easily to work with values via one component only.

Anastigmatic answered 10/10, 2018 at 7:3 Comment(3)
The custom cell editor knows nothing about another cell. That's why I have implemented the valudation in my component module. The component module knows the business logic better than the custom cell editor. Do you mean that?Cenac
This is basically the right answer, going to add a couple of examples just for clarityRoshelle
@un.spike: "you could try to combine them inside one cell and it would be easily to work with values via one component only". What are you meaning? Do you have an example? I am doing the validation right now in the GridComponent via ValueSetter, don't in CustomCellEditorPerdu
C
5

You could override the valueSetter and call the grid api transaction update instead.

Here is pseudo-code that shows how you could implement this.

valueSetter: params => {
  validate(params.newValue, onSuccess, onFail);
  return false;
};

validate = (newvalue, success, fail) => {
  if (isValid(newValue)) {
    success();
  } else {
    fail();
  }
};

onSuccess = () => {
  // do transaction update to update the cell with the new value
};

onFail = () => {
  // update some meta data property that highlights the cell signalling that the value has failed to validate
};

This way you can also do asynchronous validation. Here is a real example of an async value setter that has success, failure, and while validating handlers that do transaction updates when validation is done.

const asyncValidator = (
  newValue,
  validateFn,
  onWhileValidating,
  onSuccess,
  _onFail
) => {
  onWhileValidating();
  setTimeout(function() {
    if (validateFn(newValue)) {
      onSuccess();
    } else {
      _onFail();
    }
  }, 1000);
};

const _onWhileValidating = params => () => {
  let data = params.data;
  let field = params.colDef.field;

  data[field] = {
    ...data[field],
    isValidating: true
  };
  params.api.applyTransaction({ update: [data] });
};

const _onSuccess = params => () => {
  let data = params.data;
  let field = params.colDef.field;

  data[field] = {
    ...data[field],
    isValidating: false,
    lastValidation: true,
    value: params.newValue
  };
  params.api.applyTransaction({ update: [data] });
};

const _onFail = params => () => {
  let data = params.data;
  let field = params.colDef.field;

  data[field] = {
    ...data[field],
    isValidating: false,
    lastValidation: params.newValue
  };
  params.api.applyTransaction({ update: [data] });
};

const asyncValidateValueSetter = validateFn => params => {
  asyncValidator(
    params.newValue,
    validateFn,
    _onWhileValidating(params),
    _onSuccess(params),
    _onFail(params)
  );
  return false;
};

Here is a code runner example showing this in action: https://stackblitz.com/edit/async-validation-ag-grid-final

Camellia answered 18/11, 2020 at 11:48 Comment(1)
This forces the setter to return false therefore onCellValueChanged will not be called as usual.Gilus
R
3

Have a look at this two snippets, these come from our internal knowledge base (accessible to customers)

When editing a value in column 'A (Required)', you will see that it does not allow you to leave it empty. If you leave it empty and return the edit, it will be cancelled.

//Force Cell to require a value when finished editing

https://plnkr.co/edit/GFgb4v7P8YCW1PxJwGTx?p=preview

In this example, we are using a Custom Cell Editor that will also validate the values against a 6 character length rule. While editing, if the value is modified outside of 6 characters, it will appear in red, and when you stop editing the row, the value would be reset, so it only accepts a complete edit if the value is valid.

//Inline Validation while editing a cell 

https://plnkr.co/edit/dAAU8yLMnR8dm4vNEa9T?p=preview

Roshelle answered 12/10, 2018 at 14:8 Comment(2)
Nice examples, but you aren't doing validation between two cells. In this case the better way is the ValueStter function.Don't you think that?Perdu
Small change to the Inline Validation plnkr: <input value="${params.value}" /> will leave a / in the cell if you delete all values in the cell, tab off, and click back in. Add quotes like <input value="${params.value}" />Energize

© 2022 - 2024 — McMap. All rights reserved.