validate "required" fields

I have a solution where a user proceeds through several forms of input, then hits a final button to submit. When the user hits the Submit button, I would like the application to check to ensure that all the “required” fields have been addressed. What is the easiest way to designate certain fields as “required” and perform the check? Currently I just use a big IF statement, but I’m sure there’s a better way using validators probably.

When I initially create the field, I am unable to Un-check the “Allow Null” option. I’m not sure how that plays in to it. I’m still pretty new to Servoy. Thanks!!

Hi, It’s been a while but maybe that’s because you need Servoy 6.1 for the following solution :wink:

One way you could solve it is by using the new designTimeProperties which allow you to define custom properties for elements such as fields. In this case all you have to do is:

  1. place the checkRequiredFields function in globals
  2. Add a ‘required’ property for any element (in this example only for fields) and set it to true (see picture)
  3. Wherever you want to Save in a form add the call to checkRequiredFields and pass the form name as a parameter

Now, whenever you press Save all required fields that are empty will turn red.

function checkRequiredFields(myFormName) {
	var form = solutionModel.getForm(myFormName);
	var flds = form.getFields();
	for (item in flds) {
		var elm = flds[item];
		if (elm.getDesignTimeProperty && elm.getDesignTimeProperty('required')==true) {
			if (eval(elm.dataProviderID) == null || eval(elm.dataProviderID) == '') {
				elm.background = 'red';
			}else{
				elm.background = null; 
			}
			currentcontroller.recreateUI();
		}
	}

P.S. Yes, I used eval() but nothing dangerous gets evaluated.

[attachment=0]addDesignTimeProperty1.png[/attachment]

Or you can do it by adding ‘required’ in the name of the field and validating using that kind of method (no designTimeProperties needed, not even solutionModel and recreateUI()):

function validateRequired(formName) {
    var ok = true;
    var flds = forms[formName].elements;
    for (item in flds) {
        var elm = flds[item];
        var name = elm.getName();
        if (name.indexOf('required') > -1) {
            var dp = elm.getDataProviderID()
            if (!forms[formName].foundset.getSelectedRecord()[dp]) {
                forms[formName].elements[name].bgcolor = "#FF0000";
                ok = false;
            } else {
                forms[formName].elements[name].bgcolor = null;
            }
        }
    }
    return ok;
}

omar:
Hi, It’s been a while but maybe that’s because you need Servoy 6.1 for the following solution :wink:

One way you could solve it is by using the new designTimeProperties which allow you to define custom properties for elements such as fields. In this case all you have to do is:

  1. place the checkRequiredFields function in globals
  2. Add a ‘required’ property for any element (in this example only for fields) and set it to true (see picture)
  3. Wherever you want to Save in a form add the call to checkRequiredFields and pass the form name as a parameter

Now, whenever you press Save all required fields that are empty will turn red.

function checkRequiredFields(myFormName) {
var form = solutionModel.getForm(myFormName);
var flds = form.getFields();
for (item in flds) {
	var elm = flds[item];
	if (elm.getDesignTimeProperty && elm.getDesignTimeProperty('required')==true) {
		if (eval(elm.dataProviderID) == null || eval(elm.dataProviderID) == '') {
			elm.background = 'red';
		}else{
			elm.background = null; 
		}
		currentcontroller.recreateUI();
	}
}



P.S. Yes, I used eval() but nothing dangerous gets evaluated.

[attachment=0]addDesignTimeProperty1.png[/attachment]

Hello, I created a global method with the above code and the following fix: “for (var item in flds)”. I created a design time property “required”:“true”. If I run the global method from the forms “dc_save” method, I get the following error message:

ReferenceError: "zeichen" is not defined.

“zeichen” is the dataprovider from the related text field, which should be colored in red. The error occurs in this line:

if (eval(elm.dataProviderID) == null || eval(elm.dataProviderID) == '') {

What is the problem? I’m using Servoy 7.1.0.

Does the dataProviderId contain a valid field reference?

omar:
Does the dataProviderId contain a valid field reference?

Where / how can I check if dataProviderID contains a valid field reference?

The code above loops through the available fields on your form and evaluates the contents of the dataProvider. It looks like one of your field has “zeichen” in the dataProvider property and that it does not relate to a column in the forms table?

omar:
… evaluates the contents of the dataProvider.

The problem is the “eval()” function. The error occurs here:

eval(elm.dataProviderID)

If I put the code in the form and if I replace the code:

elm.background = 'red';

with:

forms[formName].elements[elm.name].bgcolor = 'red';

it works.

The output from the following command, if I use the function in global scope:

application.output('ProviderID: ' + elm.dataProviderID + ' Eval ProviderID: ' + eval(form[elm]));

is this:

ProviderID: zeichen Eval ProviderID: undefined

omar:
It looks like one of your field has “zeichen” in the dataProvider property and that it does not relate to a column in the forms table?

What does it mean: “that it does not relate to a column in the forms table”? The dataProvider “zeichen” is associated with the column “zeichen” from the table.

What is the problem if I use the function in global scope?

The contents of the dataProviderId are “zeichen” which refers to a column in a table. To check if the contents of the field/column “zeichen” are null it uses the eval(uate) function. This is where things go wrong. That’s why I asked if “zeichen” is a valid column in the forms table.

To bind data from a table to a control a dataProvider is used. So if application.output(zeichen) gives an error it is not a valid datasource.

omar:
The contents of the dataProviderId are “zeichen” which refers to a column in a table. To check if the contents of the field/column “zeichen” are null it uses the eval(uate) function. This is where things go wrong. That’s why I asked if “zeichen” is a valid column in the forms table.

To bind data from a table to a control a dataProvider is used. So if application.output(zeichen) gives an error it is not a valid datasource.

The field “tf_zeichen” has the dataProvider “zeichen”:

which refers to the column “zeichen” in the forms dataSource.

Is that a “valid column in the forms table”?

You would expect it to be but the error occurs for a reason. What message do you get when you add the following line of debugging code: application.output(zeichen)?

omar:
You would expect it to be but the error occurs for a reason. What message do you get when you add the following line of debugging code: application.output(zeichen)?

If I put the following code in the global function:

application.output('Zeichen: ' + forms[myFormName].zeichen);

I get the output:

Zeichen: egfv

if I have typed “egfv” in the associated text field. After that the following errors showed:

Exception Object: org.mozilla.javascript.EcmaError: ReferenceError: "zeichen" is not defined.
MSG: ReferenceError: "zeichen" is not defined.
<null>
ReferenceError: "zeichen" is not defined.
ReferenceError: "zeichen" is not defined.

Sorry, I just tried it again with a small testform and it works correctly in my situation. There must be something different in yours. Maybe you should try the method suggested by Peter Talbot?