private void loadPolicies(final IAsyncHandler<List<PolicyWithConfiguration>> handler) {
        final Set<Integer> totalCounter = new HashSet<>();
        final Set<Integer> errorCounter = new TreeSet<>();
        final List<PolicyWithConfiguration> rval = new ArrayList<>(policies.size());
        final List<Throwable> errors = new ArrayList<>(policies.size());
        final int numPolicies = policies.size();
        int index = 0;

        // If there aren't any policies, then no need to asynchronously load them!
        if (policies.isEmpty()) {
            handler.handle(policyImpls);
            return;
        }

        for (final Policy policy : policies) {
            rval.add(null);
            errors.add(null);
            final int localIdx = index++;
            policyFactory.loadPolicy(policy.getPolicyImpl(), (IAsyncResult<IPolicy> result) -> {
                if (result.isSuccess()) {
                    IPolicy policyImpl = result.getResult();
                    // Test whether pipeline contains any data policies. Connectors can use this for Content-Length pass-through.
                    if (policyImpl instanceof IDataPolicy) {
                        hasDataPolicy = true;
                    }
                    try {
                        Object policyConfig = policyFactory.loadConfig(policyImpl, policy.getPolicyImpl(), policy.getPolicyJsonConfig());
                        PolicyWithConfiguration pwc = new PolicyWithConfiguration(policyImpl, policyConfig);
                        rval.set(localIdx, pwc);
                    } catch (Throwable t) {
                        errors.set(localIdx, t);
                        errorCounter.add(localIdx);
                    }
                } else {
                    Throwable error = result.getError();
                    errors.set(localIdx, error);
                    errorCounter.add(localIdx);
                }
                totalCounter.add(localIdx);
                // Have we done them all?
                if (totalCounter.size() == numPolicies) {
                    // Did we get any errors?  If yes, report the first one. If no, then send back
                    // the fully resolved list of policies.
                    if (!errorCounter.isEmpty()) {
                        int errorIdx = errorCounter.iterator().next();
                        Throwable error = errors.get(errorIdx);
                        // TODO add some logging here to indicate which policy error'd out
                        //Policy errorPolicy = policies.get(errorIdx);
                        policyErrorHandler.handle(error);
                    } else {
                        handler.handle(rval);
                    }
                }
            });
        }
    }
Get/resolve the list of policies into a list of policies with config.  This operation is
done asynchronously so that plugins can be downloaded if needed.  Any errors in resolving
the policies will be reported back via the policyErrorHandler.
gateway/engine/core/src/main/java/io/apiman/gateway/engine/impl/ApiRequestExecutorImpl.java