001// Copyright 2011 The Apache Software Foundation
002//
003// Licensed under the Apache License, Version 2.0 (the "License");
004// you may not use this file except in compliance with the License.
005// You may obtain a copy of the License at
006//
007// http://www.apache.org/licenses/LICENSE-2.0
008//
009// Unless required by applicable law or agreed to in writing, software
010// distributed under the License is distributed on an "AS IS" BASIS,
011// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
012// See the License for the specific language governing permissions and
013// limitations under the License.
014
015package org.apache.tapestry5.internal.jpa;
016
017import javax.persistence.EntityManager;
018import javax.persistence.PersistenceContext;
019
020import org.apache.tapestry5.ioc.AnnotationProvider;
021import org.apache.tapestry5.ioc.ObjectCreator;
022import org.apache.tapestry5.ioc.ObjectLocator;
023import org.apache.tapestry5.ioc.ObjectProvider;
024import org.apache.tapestry5.ioc.services.ClassFactory;
025import org.apache.tapestry5.jpa.EntityManagerManager;
026
027public class EntityManagerObjectProvider implements ObjectProvider
028{
029
030    private EntityManager proxy;
031
032    /**
033     * {@inheritDoc}
034     */
035    public <T> T provide(final Class<T> objectType, final AnnotationProvider annotationProvider,
036            final ObjectLocator locator)
037    {
038        if (objectType.equals(EntityManager.class))
039            return objectType.cast(getOrCreateProxy(annotationProvider, locator));
040
041        return null;
042    }
043
044    private synchronized EntityManager getOrCreateProxy(
045            final AnnotationProvider annotationProvider, final ObjectLocator objectLocator)
046    {
047        if (proxy == null)
048        {
049            final ClassFactory classFactory = objectLocator.getService("ClassFactory",
050                    ClassFactory.class);
051
052             final PersistenceContext annotation = annotationProvider
053                            .getAnnotation(PersistenceContext.class);
054
055            proxy = classFactory.createProxy(EntityManager.class, new ObjectCreator()
056            {
057                public Object createObject()
058                {
059                    final EntityManagerManager entityManagerManager = objectLocator
060                            .getService(EntityManagerManager.class);
061
062                    return JpaInternalUtils.getEntityManager(entityManagerManager, annotation);
063                }
064            }, "<EntityManagerProxy>");
065        }
066
067        return proxy;
068    }
069
070}