/* * JBoss, Home of Professional Open Source. * Copyright 2014, Red Hat Middleware LLC, and individual contributors * as indicated by the @author tags. See the copyright.txt file in the * distribution for a full listing of individual contributors. * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU Lesser General Public License as * published by the Free Software Foundation; either version 2.1 of * the License, or (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this software; if not, write to the Free * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA * 02110-1301 USA, or see the FSF site: http://www.fsf.org. */ package org.jboss.as.ejb3.timerservice.persistence.filestore; import java.io.ByteArrayOutputStream; import java.util.Base64; import java.util.List; import javax.xml.stream.XMLStreamException; import org.jboss.as.ejb3.logging.EjbLogger; import org.jboss.as.ejb3.timerservice.CalendarTimer; import org.jboss.as.ejb3.timerservice.TimerImpl; import org.jboss.marshalling.Marshaller; import org.jboss.marshalling.MarshallerFactory; import org.jboss.marshalling.MarshallingConfiguration; import org.jboss.marshalling.OutputStreamByteOutput; import org.jboss.staxmapper.XMLElementWriter; import org.jboss.staxmapper.XMLExtendedStreamWriter; /** * @author Stuart Douglas */ public class EjbTimerXmlPersister implements XMLElementWriter<List<TimerImpl>> { static final String TIMERS = "timers"; static final String TIMER = "timer"; static final String CALENDAR_TIMER = "calendar-timer"; static final String INFO = "info"; static final String PRIMARY_KEY = "primary-key"; static final String TIMED_OBJECT_ID = "timed-object-id"; static final String TIMER_ID = "timer-id"; static final String INITIAL_DATE = "initial-date"; static final String REPEAT_INTERVAL = "repeat-interval"; static final String NEXT_DATE = "next-date"; static final String PREVIOUS_RUN = "previous-run"; static final String TIMER_STATE = "timer-state"; static final String TIMEOUT_METHOD = "timeout-method"; static final String SCHEDULE_EXPR_SECOND = "schedule-expr-second"; static final String SCHEDULE_EXPR_MINUTE = "schedule-expr-minute"; static final String SCHEDULE_EXPR_HOUR = "schedule-expr-hour"; static final String SCHEDULE_EXPR_DAY_OF_WEEK = "schedule-expr-day-of-week"; static final String SCHEDULE_EXPR_DAY_OF_MONTH = "schedule-expr-day-of-month"; static final String SCHEDULE_EXPR_MONTH = "schedule-expr-month"; static final String SCHEDULE_EXPR_YEAR = "schedule-expr-year"; static final String SCHEDULE_EXPR_START_DATE = "schedule-expr-start-date"; static final String SCHEDULE_EXPR_END_DATE = "schedule-expr-end-date"; static final String SCHEDULE_EXPR_TIMEZONE = "schedule-expr-timezone"; static final String PARAMETER = "parameter"; static final String DECLARING_CLASS = "declaring-class"; static final String NAME = "name"; static final String TYPE = "type"; private final MarshallerFactory factory; private final MarshallingConfiguration configuration; public EjbTimerXmlPersister(MarshallerFactory factory, MarshallingConfiguration configuration) { this.factory = factory; this.configuration = configuration; } @Override public void writeContent(XMLExtendedStreamWriter writer, List<TimerImpl> timers) throws XMLStreamException { writer.writeStartDocument(); writer.writeStartElement(TIMERS); writer.writeDefaultNamespace(EjbTimerXmlParser_1_0.NAMESPACE); for (TimerImpl timer : timers) { if (timer instanceof CalendarTimer) { writeCalendarTimer(writer, (CalendarTimer) timer); } else { writeTimer(writer, timer); } } writer.writeEndElement(); writer.writeEndDocument(); } private void writeCalendarTimer(XMLExtendedStreamWriter writer, CalendarTimer timer) throws XMLStreamException { String info = null; String primaryKey = null; if (timer.getInfo() != null) { try { Marshaller marshaller = factory.createMarshaller(configuration); ByteArrayOutputStream out = new ByteArrayOutputStream(); marshaller.start(new OutputStreamByteOutput(out)); marshaller.writeObject(timer.getInfo()); marshaller.finish(); marshaller.flush(); info = Base64.getEncoder().encodeToString(out.toByteArray()); } catch (Exception e) { EjbLogger.EJB3_TIMER_LOGGER.failedToPersistTimer(timer, e); return; } } if (timer.getPrimaryKey() != null) { try { Marshaller marshaller = factory.createMarshaller(configuration); ByteArrayOutputStream out = new ByteArrayOutputStream(); marshaller.start(new OutputStreamByteOutput(out)); marshaller.writeObject(timer.getPrimaryKey()); marshaller.finish(); marshaller.flush(); primaryKey = Base64.getEncoder().encodeToString(out.toByteArray()); } catch (Exception e) { EjbLogger.EJB3_TIMER_LOGGER.failedToPersistTimer(timer, e); return; } } writer.writeStartElement(CALENDAR_TIMER); writer.writeAttribute(TIMED_OBJECT_ID, timer.getTimedObjectId()); writer.writeAttribute(TIMER_ID, timer.getId()); if (timer.getInitialExpiration() != null) { writer.writeAttribute(INITIAL_DATE, Long.toString(timer.getInitialExpiration().getTime())); } if(timer.getNextExpiration() != null) { writer.writeAttribute(NEXT_DATE, Long.toString(timer.getNextExpiration().getTime())); } writer.writeAttribute(TIMER_STATE, timer.getState().name()); writer.writeAttribute(SCHEDULE_EXPR_SECOND, timer.getScheduleExpression().getSecond()); writer.writeAttribute(SCHEDULE_EXPR_MINUTE, timer.getScheduleExpression().getMinute()); writer.writeAttribute(SCHEDULE_EXPR_HOUR, timer.getScheduleExpression().getHour()); writer.writeAttribute(SCHEDULE_EXPR_DAY_OF_WEEK, timer.getScheduleExpression().getDayOfWeek()); writer.writeAttribute(SCHEDULE_EXPR_DAY_OF_MONTH, timer.getScheduleExpression().getDayOfMonth()); writer.writeAttribute(SCHEDULE_EXPR_MONTH, timer.getScheduleExpression().getMonth()); writer.writeAttribute(SCHEDULE_EXPR_YEAR, timer.getScheduleExpression().getYear()); if (timer.getScheduleExpression().getStart() != null) { writer.writeAttribute(SCHEDULE_EXPR_START_DATE, Long.toString(timer.getScheduleExpression().getStart().getTime())); } if (timer.getScheduleExpression().getEnd() != null) { writer.writeAttribute(SCHEDULE_EXPR_END_DATE, Long.toString(timer.getScheduleExpression().getEnd().getTime())); } if (timer.getScheduleExpression().getTimezone() != null) { writer.writeAttribute(SCHEDULE_EXPR_TIMEZONE, timer.getScheduleExpression().getTimezone()); } if (info != null) { writer.writeStartElement(INFO); writer.writeCharacters(info); writer.writeEndElement(); } if (primaryKey != null) { writer.writeStartElement(PRIMARY_KEY); writer.writeCharacters(primaryKey); writer.writeEndElement(); } if (timer.isAutoTimer()) { writer.writeStartElement(TIMEOUT_METHOD); writer.writeAttribute(DECLARING_CLASS, timer.getTimeoutMethod().getDeclaringClass().getName()); writer.writeAttribute(NAME, timer.getTimeoutMethod().getName()); for (Class<?> param : timer.getTimeoutMethod().getParameterTypes()) { writer.writeStartElement(PARAMETER); writer.writeAttribute(TYPE, param.getName()); writer.writeEndElement(); } writer.writeEndElement(); } writer.writeEndElement(); } private void writeTimer(XMLExtendedStreamWriter writer, TimerImpl timer) throws XMLStreamException { String info = null; String primaryKey = null; if (timer.getInfo() != null) { try { Marshaller marshaller = factory.createMarshaller(configuration); ByteArrayOutputStream out = new ByteArrayOutputStream(); marshaller.start(new OutputStreamByteOutput(out)); marshaller.writeObject(timer.getInfo()); marshaller.finish(); marshaller.flush(); info = Base64.getEncoder().encodeToString(out.toByteArray()); } catch (Exception e) { EjbLogger.EJB3_TIMER_LOGGER.failedToPersistTimer(timer, e); return; } } if (timer.getPrimaryKey() != null) { try { Marshaller marshaller = factory.createMarshaller(configuration); ByteArrayOutputStream out = new ByteArrayOutputStream(); marshaller.start(new OutputStreamByteOutput(out)); marshaller.writeObject(timer.getPrimaryKey()); marshaller.finish(); marshaller.flush(); primaryKey = Base64.getEncoder().encodeToString(out.toByteArray()); } catch (Exception e) { EjbLogger.EJB3_TIMER_LOGGER.failedToPersistTimer(timer, e); return; } } writer.writeStartElement(TIMER); writer.writeAttribute(TIMED_OBJECT_ID, timer.getTimedObjectId()); writer.writeAttribute(TIMER_ID, timer.getId()); writer.writeAttribute(INITIAL_DATE, Long.toString(timer.getInitialExpiration().getTime())); writer.writeAttribute(REPEAT_INTERVAL, Long.toString(timer.getInterval())); if(timer.getNextExpiration() != null) { writer.writeAttribute(NEXT_DATE, Long.toString(timer.getNextExpiration().getTime())); } writer.writeAttribute(TIMER_STATE, timer.getState().name()); if (info != null) { writer.writeStartElement(INFO); writer.writeCharacters(info); writer.writeEndElement(); } if (primaryKey != null) { writer.writeStartElement(PRIMARY_KEY); writer.writeCharacters(primaryKey); writer.writeEndElement(); } writer.writeEndElement(); } }