/* * Copyright (c) 2004-2011 Marco Maccaferri and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Marco Maccaferri - initial API and implementation */ package org.eclipsetrader.repository.hibernate.internal.stores; import java.net.URI; import java.net.URISyntaxException; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import javax.persistence.CascadeType; import javax.persistence.Column; import javax.persistence.DiscriminatorColumn; import javax.persistence.DiscriminatorType; import javax.persistence.DiscriminatorValue; import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.Id; import javax.persistence.Inheritance; import javax.persistence.InheritanceType; import javax.persistence.OneToMany; import javax.persistence.Table; import javax.persistence.Transient; import javax.persistence.Version; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Status; import org.eclipsetrader.core.feed.IHistory; import org.eclipsetrader.core.feed.IOHLC; import org.eclipsetrader.core.feed.ISplit; import org.eclipsetrader.core.feed.TimeSpan; import org.eclipsetrader.core.instruments.ISecurity; import org.eclipsetrader.core.repositories.IPropertyConstants; import org.eclipsetrader.core.repositories.IRepository; import org.eclipsetrader.core.repositories.IRepositoryService; import org.eclipsetrader.core.repositories.IStore; import org.eclipsetrader.core.repositories.IStoreObject; import org.eclipsetrader.core.repositories.IStoreProperties; import org.eclipsetrader.core.repositories.StoreProperties; import org.eclipsetrader.repository.hibernate.HibernateRepository; import org.eclipsetrader.repository.hibernate.internal.Activator; import org.eclipsetrader.repository.hibernate.internal.types.HistoryData; import org.eclipsetrader.repository.hibernate.internal.types.SecurityType; import org.eclipsetrader.repository.hibernate.internal.types.SplitData; import org.hibernate.Query; import org.hibernate.Session; import org.hibernate.annotations.Cascade; import org.hibernate.annotations.GenericGenerator; import org.hibernate.annotations.Target; import org.osgi.framework.BundleContext; import org.osgi.framework.ServiceReference; @Entity @Table(name = "histories") @Inheritance(strategy = InheritanceType.SINGLE_TABLE) @DiscriminatorColumn(name = "type", discriminatorType = DiscriminatorType.STRING, length = 16) @DiscriminatorValue("history") public class HistoryStore implements IStore { @Id @Column(name = "id", length = 32) @GeneratedValue(generator = "system-uuid") @GenericGenerator(name = "system-uuid", strategy = "uuid") String id; @Version @Column(name = "version") @SuppressWarnings("unused") private Integer version; @Column(name = "instrument") @Target(SecurityType.class) ISecurity security; @OneToMany(mappedBy = "history", cascade = CascadeType.ALL) @Cascade(org.hibernate.annotations.CascadeType.DELETE_ORPHAN) List<HistoryData> data = new ArrayList<HistoryData>(); @OneToMany(mappedBy = "history", cascade = CascadeType.ALL) @Cascade(org.hibernate.annotations.CascadeType.DELETE_ORPHAN) private List<SplitData> splits = new ArrayList<SplitData>(); @Transient HibernateRepository repository; public HistoryStore() { } public HistoryStore(ISecurity security, HibernateRepository repository) { this.repository = repository; this.security = security; } public void setRepository(HibernateRepository repository) { this.repository = repository; } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#fetchProperties(org.eclipse.core.runtime.IProgressMonitor) */ @Override public IStoreProperties fetchProperties(IProgressMonitor monitor) { StoreProperties properties = new StoreProperties(); properties.setProperty(IPropertyConstants.OBJECT_TYPE, IHistory.class.getName()); properties.setProperty(IPropertyConstants.SECURITY, security); properties.setProperty(IPropertyConstants.TIME_SPAN, TimeSpan.days(1)); properties.setProperty(IPropertyConstants.BARS, data.toArray(new IOHLC[data.size()])); properties.setProperty(IPropertyConstants.SPLITS, splits.toArray(new ISplit[splits.size()])); return properties; } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#putProperties(org.eclipsetrader.core.repositories.IStoreProperties, org.eclipse.core.runtime.IProgressMonitor) */ @Override public void putProperties(IStoreProperties properties, IProgressMonitor monitor) { Session session = repository.getSession(); this.security = (ISecurity) properties.getProperty(IPropertyConstants.SECURITY); List<HistoryData> newData = new ArrayList<HistoryData>(2048); IOHLC[] bars = (IOHLC[]) properties.getProperty(IPropertyConstants.BARS); if (bars != null) { TimeSpan timeSpan = TimeSpan.days(1); for (int i = 0; i < bars.length; i++) { newData.add(new HistoryData(this, bars[i], timeSpan)); } } for (HistoryData ohlc : newData) { if (!this.data.contains(ohlc)) { this.data.add(ohlc); } } for (Iterator<HistoryData> iter = this.data.iterator(); iter.hasNext();) { if (!newData.contains(iter.next())) { iter.remove(); } } ISplit[] s = (ISplit[]) properties.getProperty(IPropertyConstants.SPLITS); splits.clear(); if (s != null) { for (int i = 0; i < s.length; i++) { splits.add(new SplitData(this, s[i])); } } session.save(this); } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#delete(org.eclipse.core.runtime.IProgressMonitor) */ @Override public void delete(IProgressMonitor monitor) throws CoreException { } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#fetchChilds(org.eclipse.core.runtime.IProgressMonitor) */ @Override @SuppressWarnings("unchecked") public IStore[] fetchChilds(IProgressMonitor monitor) { List<IStore> l = new ArrayList<IStore>(); Query query = repository.getSession().createQuery("from IntradayHistoryStore where instrument = :instrument"); IStoreObject storeObject = (IStoreObject) security.getAdapter(IStoreObject.class); query.setString("instrument", storeObject.getStore().toURI().toString()); List list = query.list(); if (list != null) { for (Object o : list) { l.add((IStore) o); } } return l.toArray(new IStore[l.size()]); } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#createChild() */ @Override public IStore createChild() { return new IntradayHistoryStore(security, repository); } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#toURI() */ @Override public URI toURI() { try { return new URI(repository.getSchema(), HibernateRepository.URI_SECURITY_HISTORY_PART, id); } catch (URISyntaxException e) { e.printStackTrace(); } return null; } /* (non-Javadoc) * @see org.eclipsetrader.core.repositories.IStore#getRepository() */ @Override public IRepository getRepository() { return repository; } protected ISecurity getSecurityFromURI(URI uri) { ISecurity security = null; try { BundleContext context = Activator.getDefault().getBundle().getBundleContext(); ServiceReference serviceReference = context.getServiceReference(IRepositoryService.class.getName()); IRepositoryService repositoryService = (IRepositoryService) context.getService(serviceReference); security = repositoryService.getSecurityFromURI(uri); if (security != null) { Status status = new Status(IStatus.WARNING, Activator.PLUGIN_ID, 0, "Failed to load security " + uri.toString(), null); Activator.log(status); } context.ungetService(serviceReference); } catch (Exception e) { Status status = new Status(IStatus.ERROR, Activator.PLUGIN_ID, 0, "Error reading repository service", e); Activator.log(status); } return security; } }