001/* 002 * (C) Copyright 2017 Nuxeo (http://nuxeo.com/) and others. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 * 016 * Contributors: 017 * Kevin Leturc <[email protected]> 018 */ 019package org.nuxeo.runtime; 020 021import java.util.ArrayList; 022import java.util.Collections; 023import java.util.List; 024import java.util.logging.Level; 025import java.util.stream.Collectors; 026 027import org.nuxeo.runtime.model.ComponentManager; 028 029/** 030 * Handles runtime messages by taking care of component manager lifecycle in order to work correctly with hot reload. 031 * This is interesting to not store several time the same message in case of hot reload. 032 * 033 * @since 9.10 034 */ 035public class RuntimeMessageHandlerImpl implements RuntimeMessageHandler, ComponentManager.Listener { 036 037 protected final List<Message> messages = new ArrayList<>(); 038 039 protected ComponentManagerStep step = ComponentManagerStep.ACTIVATING; 040 041 @Override 042 public void addWarning(String message) { 043 messages.add(new Message(step, Level.WARNING, message)); 044 } 045 046 @Override 047 public List<String> getWarnings() { 048 return messages.stream().filter(msg -> Level.WARNING.equals(msg.getLevel())).map(Message::getMessage).collect( 049 Collectors.collectingAndThen(Collectors.toList(), Collections::unmodifiableList)); 050 } 051 052 @Override 053 public void addError(String message) { 054 messages.add(new Message(step, Level.SEVERE, message)); 055 } 056 057 @Override 058 public List<String> getErrors() { 059 return messages.stream().filter(msg -> Level.SEVERE.equals(msg.getLevel())).map(Message::getMessage).collect( 060 Collectors.collectingAndThen(Collectors.toList(), Collections::unmodifiableList)); 061 } 062 063 @Override 064 public void beforeActivation(ComponentManager mgr) { 065 changeStep(ComponentManagerStep.ACTIVATING); 066 } 067 068 @Override 069 public void beforeStart(ComponentManager mgr, boolean isResume) { 070 changeStep(ComponentManagerStep.STARTING); 071 } 072 073 @Override 074 public void afterStart(ComponentManager mgr, boolean isResume) { 075 changeStep(ComponentManagerStep.RUNNING); 076 } 077 078 @Override 079 public void beforeStop(ComponentManager mgr, boolean isStandby) { 080 changeStep(ComponentManagerStep.STOPPING); 081 } 082 083 @Override 084 public void beforeDeactivation(ComponentManager mgr) { 085 changeStep(ComponentManagerStep.DEACTIVATING); 086 } 087 088 protected void changeStep(ComponentManagerStep step) { 089 messages.removeIf(msg -> step.equals(msg.getStep())); 090 this.step = step; 091 } 092 093 /** 094 * @since 9.10 095 */ 096 protected static class Message { 097 098 protected final ComponentManagerStep step; 099 100 protected final Level level; 101 102 protected final String message; 103 104 public Message(ComponentManagerStep step, Level level, String message) { 105 this.step = step; 106 this.level = level; 107 this.message = message; 108 } 109 110 public ComponentManagerStep getStep() { 111 return step; 112 } 113 114 public Level getLevel() { 115 return level; 116 } 117 118 public String getMessage() { 119 return message; 120 } 121 122 } 123 124 /** 125 * @since 9.10 126 */ 127 protected enum ComponentManagerStep { 128 129 ACTIVATING, 130 131 STARTING, 132 133 RUNNING, 134 135 STOPPING, 136 137 DEACTIVATING 138 139 } 140 141}