private Result createObject()

in src/main/java/org/apache/sling/models/impl/ModelAdapterFactory.java [722:799]


    private <ModelType> Result<ModelType> createObject(final Object adaptable, final ModelClass<ModelType> modelClass)
            throws InstantiationException, InvocationTargetException, IllegalAccessException {
        DisposalCallbackRegistryImpl registry = new DisposalCallbackRegistryImpl();

        ModelClassConstructor<ModelType> constructorToUse = getBestMatchingConstructor(adaptable, modelClass);
        if (constructorToUse == null) {
            return new Result<>(new ModelClassException("Unable to find a useable constructor for model " + modelClass.getType()));
        }

        final Map<ValuePreparer, Object> preparedValues = new HashMap<>(VALUE_PREPARERS_COUNT);

        ModelType object;
        if (constructorToUse.getConstructor().getParameterTypes().length == 0) {
            // no parameters for constructor injection? instantiate it right away

            object = constructorToUse.newInstance();
        } else {
            // instantiate with constructor injection
            // if this fails, make sure resources that may be claimed by injectors are cleared up again
            try {
                Result<ModelType> result = newInstanceWithConstructorInjection(constructorToUse, adaptable, modelClass, registry, preparedValues);
                if (!result.wasSuccessful()) {
                    registry.onDisposed();
                    return result;
                } else {
                    object = result.getValue();
                }
            } catch (InstantiationException | InvocationTargetException | IllegalAccessException ex) {
                registry.onDisposed();
                throw ex;
            }
        }

        InjectCallback callback = new SetFieldCallback(object);

        InjectableField[] injectableFields = modelClass.getInjectableFields();
        List<MissingElementException> missingElements = null;
        final BundleContext modelContext = getModelBundleContext(modelClass);
        for (InjectableField field : injectableFields) {
            RuntimeException t = injectElement(field, adaptable, registry, callback, preparedValues, modelContext);
            if (t != null) {
                if (missingElements == null) {
                    missingElements = new ArrayList<>();
                }
                missingElements.add(new MissingElementException(field.getAnnotatedElement(), t));
            }
        }

        if (!registry.callbacks.isEmpty()) {
            registry.seal();

            if (adaptable instanceof SlingHttpServletRequest &&
                    ((SlingHttpServletRequest) adaptable).getAttribute(REQUEST_MARKER_ATTRIBUTE) == REQUEST_MARKER_VALUE) {
                registerRequestCallbackRegistry((SlingHttpServletRequest) adaptable, registry);
            } else {
                registerCallbackRegistry(object, registry);
            }

        }
        if (missingElements != null) {
            MissingElementsException missingElementsException = new MissingElementsException("Could not inject all required fields into " + modelClass.getType());
            for (MissingElementException me : missingElements) {
                missingElementsException.addMissingElementExceptions(me);
            }
            return new Result<>(missingElementsException);
        }
        try {
            object = invokePostConstruct(object);
            if (object == null) {
                return (Result<ModelType>) Result.POST_CONSTRUCT_PREVENTED_MODEL_CONSTRUCTION;
            }
        } catch (InvocationTargetException e) {
            return new Result<>(new PostConstructException("Post-construct method has thrown an exception for model " + modelClass.getType(), e.getCause()));
        } catch (IllegalAccessException e) {
            new Result<ModelType>(new ModelClassException("Could not call post-construct method for model " + modelClass.getType(), e));
        }
        return new Result<>(object);
    }