<MyAddFieldPlugin Project>/src/org/myorg/myaddfieldplugin/AddAtomCountFieldAction.java
    private static void fillData(final DFField newField) {

        // get entity for the given field (parent object in DDL is always accessible)
        final DFEntity entity = newField.getEntity();

        // find field which contains molecules. We can recognize it using appropriate capability
        final DFField structureField = findStructureField(entity);

        // get the id (unique identifier) of any DFItem - in this case structure field. The field id can be
        // used when obtaining data
        final String structureFieldId = structureField.getId();

        // Data provider is the basic class for obtaining data from an entity (database table).
        // It can be found from DFSchema using a few method calls or directly using this utility method
        final DFEntityDataProvider edp = DIFUtilities.findEntityDataProvider(entity);

        String fillingDataTaskName = NbBundle.getMessage(AddAtomCountFieldAction.class, "MSG_ProgressNameFillingData");

        // Filling data should be again done on background. Currently we run in AWT thread
        // (as this method was called from phase2InAWT in createNewField)
        // Now we use a different lockable - each EDP has its own lockable (opposite to DDL operations which shares the same
        // lockable object for whole DFSchema)
        // Filling the data is now cancellable.
        //
        // Note: As alternative to current phase1InRequestProcessor method (see below) you can use BatchUpdateIterator helper class
        UIBackgroundRunnerRW runner = new UIBackgroundRunnerRW(DIFUtilities.getLockable(edp), fillingDataTaskName, true) {
            @Override
            public void phase1InRequestProcessor() {

                // Through current DFFeedback we can present the current progress to user
                DFFeedback feedback = getEnvironment().getFeedback();
                feedback.addMessage(DFFeedback.Type.PROGRESS_MESSAGE,NbBundle.getMessage(AddAtomCountFieldAction.class, "MSG_ProgressGrabbingData"), null);

                // Get values of primary key for all data in the table first
                List<? extends Comparable<?>> ids = edp.queryForIds(DFTermExpression.ALL_DATA, SortDirective.EMPTY, getEnvironment());

                Map<String,Object> valuesToUpdate = new HashMap<String,Object>();

                int total = ids.size();

                // switch progress to determinate mode and start counting
                feedback.switchToDeterminate(total);
                int counter = 0;

                // Iterate for all row primary key values
                for (Comparable<?> rowId: ids) {
                    if (getEnvironment().getFeedback().isCancelled()) {
                        throw new CancelException(NbBundle.getMessage(AddAtomCountFieldAction.class, "MSG_TaskCancelled", counter, total));
                    }

                    // Get the current row data ... if we need only a single row data the returned Map will have only one entry...
                    Map<Comparable<?>, Map<String, Object>> allData = edp.getData(Collections.singletonList(rowId), getEnvironment());

                    // ... the entry for the given rowId, which is again a Map: keys are id's of fields in the entity and values are the
                    // real data in each cell in database
                    Object structureValue = allData.get(rowId).get(structureFieldId);
                    int atomCount = 0;

                    // If the molecule object is of known type...
                    if (structureValue instanceof MarvinStructure) {
                        // ... we can count the atoms
                        Molecule mol = ((MarvinStructure) structureValue).getNative();
                        atomCount = mol.getAtomCount();
                        atomCount += mol.getImplicitHcount();
                        atomCount += mol.getExplicitHcount();
                    }

                    // ... and update the value in the new field
                    valuesToUpdate.put(newField.getId(), atomCount);

                    // create DFUpdateDescription instance which describes one update call
                    DFUpdateDescription updateDescr = DFUpdateDescription.create(entity, rowId, valuesToUpdate);

                    // perform update operation
                    DFUpdateResult result = edp.update(Collections.singletonList(updateDescr), DFUndoConfig.OFF, getEnvironment()).get(updateDescr);

                    // and check the result
                    if (!result.isSuccessful()) {
                        throw new RuntimeException(result.getException());
                    }

                    feedback.progress(counter);
                    feedback.addMessage(DFFeedback.Type.PROGRESS_MESSAGE,NbBundle.getMessage(AddAtomCountFieldAction.class, "MSG_ProgressFillingDataDetail", counter, total), null);
                    counter++;
                }
                feedback.addMessage(DFFeedback.Type.STATUS_BAR_MESSAGE,NbBundle.getMessage(AddAtomCountFieldAction.class, "StatusBar_TaskDone"), null);
            }

            @Override
            public boolean phase1Cancelled(CancelException exc) {
                DialogDisplayer.getDefault().notify(new DialogDescriptor.Message(exc.getMessage()));
                return false;
            }

            @Override
            public void phase2InAWT() {
                DialogDisplayer.getDefault().notify(new DialogDescriptor.Message(NbBundle.getMessage(AddAtomCountFieldAction.class, "MSG_TaskDone")));
            }
        };
        runner.start();

    }