You are viewing a plain text version of this content. The canonical link for it is here.
Posted to slide-dev@jakarta.apache.org by df...@apache.org on 2004/05/13 15:30:53 UTC

cvs commit: jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector Connector.java Subscriber.java

dflorey     2004/05/13 06:30:52

  Modified:    proposals/projector/src/java/org/apache/slide/projector/engine
                        Scheduler.java ApplicationListener.java
                        ProcessorManager.java Application.java
                        ApplicationManager.java
               proposals/projector/src/java/org/apache/slide/projector/i18n
                        MessageManager.java
               proposals/projector/src/java/org/apache/slide/projector/connector/webdav
                        WebdavDispatcher.java WebdavConnector.java
               proposals/projector/src/java/org/apache/slide/projector/connector
                        Connector.java Subscriber.java
  Log:
  Improved application handling (works for transactional application installation)
  
  Revision  Changes    Path
  1.2       +91 -41    jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/Scheduler.java
  
  Index: Scheduler.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/Scheduler.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- Scheduler.java	3 May 2004 14:20:20 -0000	1.1
  +++ Scheduler.java	13 May 2004 13:30:52 -0000	1.2
  @@ -26,6 +26,7 @@
   
       private final static String SCHEDULER_CONFIG = "scheduler.xml";
       private final static String JOBS = "jobs.xml";
  +   	private final Context context = new SystemContext();
   
       private static Scheduler scheduler = new Scheduler();
       private static ThreadLocal threadContext = new ThreadLocal();
  @@ -35,57 +36,106 @@
       private ExpressionFactory expressionFactory = new ExpressionFactory();
   
       static {
  -        ConnectorFactory.getConnector().subscribe("Update", Constants.DOMAIN,
  +        ConnectorFactory.getConnector().subscribe("Update", new URIResource(Constants.DOMAIN),
                   0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, scheduler, Constants.CREDENTIALS);
       }
   
       private List jobs = new ArrayList();
  -
  +    private Map installedJobs = new HashMap();
  +    
       private Scheduler() {
  -        final Context context = new SystemContext();
  -        logger.log(Level.INFO, "Parsing scheduler configuration");
  -        try {
  -            InputStream configuration = ((StreamableResource)ConnectorFactory.getConnector().getResource(new URIResource(Constants.CONFIG_DIR + SCHEDULER_CONFIG), context.getCredentials())).getInputStream();
  -            InputStream jobs = ((StreamableResource)ConnectorFactory.getConnector().getResource(new URIResource(Constants.CONFIG_DIR + SCHEDULER_CONFIG), context.getCredentials())).getInputStream();
  -            SimpleImporter importer = new SimpleImporter();
  -            StepConfigurationHandler handler = new StepConfigurationHandler(jobConfigurations, expressionFactory);
  -            importer.addSimpleImportHandler(handler);
  -            importer.addSimpleImportHandler(expressionFactory);
  -            importer.parse(new InputSource(configuration));
  -            importer.parse(new InputSource(jobs));
  -            for ( Iterator i = jobConfigurations.values().iterator(); i.hasNext(); ) {
  -                Step jobConfiguration = (Step)i.next();
  -                Processor processor = ProcessorManager.getInstance().getProcessor(jobConfiguration.getProcessorURI());
  -                Map processorParameters = new HashMap();
  -                ParameterDescriptor[] parameterDescriptors = processor.getParameterDescriptors();
  -                for (int j = 0; j < parameterDescriptors.length; j++) {
  -                    // validate...
  -                    ParameterDescriptor parameterDescriptor = parameterDescriptors[j];
  -                    ParameterConfiguration parameterConfiguration = (ParameterConfiguration)jobConfiguration.getParameterConfigurations().get(parameterDescriptor.getName());
  -                    if (parameterConfiguration == null && parameterDescriptor.isRequired()) {
  -                        logger.log(Level.SEVERE, "Required parameter '" + parameterDescriptor.getName() + "' not assigned in job '" + jobConfiguration + "'!");
  -                        throw new ProcessException(new ErrorMessage("requiredParameterMissing", new String[]{parameterDescriptor.getName()}));
  -                    } else {
  -                        if ( parameterConfiguration != null ) {
  -                            Resource validatedValue = parameterConfiguration.getValidatedValue(parameterDescriptor, new HashMap(), null, context);
  -                            if ( validatedValue != null ) {
  -                                processorParameters.put(parameterDescriptor.getName(), validatedValue);
  -                            }
  -                        }
  -                    }
  -                }
  -                addJob(jobConfiguration.getExpression(), jobConfiguration.getProcessorURI(), processorParameters, jobConfiguration.repeat(), jobConfiguration.isPersistent());
  -            }
  -        } catch (Exception exception) {
  -            logger.log(Level.SEVERE, "Error while parsing configuration", exception);
  -        }
  -
       }
   
       public static Scheduler getInstance() {
           return scheduler;
       }
   
  +    public void install(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		install(configurationUri);
  +    	}
  +    }
  +    
  +    public void uninstall(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		uninstall(configurationUri);
  +    	}
  +    }
  +    
  +    public void update(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		update(configurationUri);
  +    	}
  +    }
  +    
  +    public void install(URI jobsUri) {
  +    	logger.log(Level.INFO, "Installing scheduled jobs of application '"+jobsUri+"'");
  +    	try {
  +    		Map applicationJobs = new HashMap();
  +    		StreamableResource jobsResource = (StreamableResource)ConnectorFactory.getConnector().getResource(jobsUri, Constants.CREDENTIALS);
  +    		if ( jobsResource != null ) {
  +    			InputStream jobsInputStream = jobsResource.getInputStream();
  +    			SimpleImporter importer = new SimpleImporter();
  +    			StepConfigurationHandler handler = new StepConfigurationHandler(jobConfigurations, expressionFactory);
  +    			importer.addSimpleImportHandler(handler);
  +    			importer.addSimpleImportHandler(expressionFactory);
  +    			importer.parse(new InputSource(jobsInputStream));
  +    			for ( Iterator i = jobConfigurations.values().iterator(); i.hasNext(); ) {
  +    				Step jobConfiguration = (Step)i.next();
  +    				Processor processor = ProcessorManager.getInstance().getProcessor(jobConfiguration.getProcessorURI());
  +    				Map processorParameters = new HashMap();
  +    				ParameterDescriptor[] parameterDescriptors = processor.getParameterDescriptors();
  +    				for (int j = 0; j < parameterDescriptors.length; j++) {
  +    					// validate...
  +    					ParameterDescriptor parameterDescriptor = parameterDescriptors[j];
  +    					ParameterConfiguration parameterConfiguration = (ParameterConfiguration)jobConfiguration.getParameterConfigurations().get(parameterDescriptor.getName());
  +    					if (parameterConfiguration == null && parameterDescriptor.isRequired()) {
  +    						logger.log(Level.SEVERE, "Required parameter '" + parameterDescriptor.getName() + "' not assigned in job '" + jobConfiguration + "'!");
  +    						throw new ProcessException(new ErrorMessage("requiredParameterMissing", new String[]{parameterDescriptor.getName()}));
  +    					} else {
  +    						if ( parameterConfiguration != null ) {
  +    							Resource validatedValue = parameterConfiguration.getValidatedValue(parameterDescriptor, new HashMap(), null, context);
  +    							if ( validatedValue != null ) {
  +    								processorParameters.put(parameterDescriptor.getName(), validatedValue);
  +    							}
  +    						}
  +    					}
  +    				}
  +    				addJob(jobConfiguration.getExpression(), jobConfiguration.getProcessorURI(), processorParameters, jobConfiguration.repeat(), jobConfiguration.isPersistent());
  +    			}
  +    			ConnectorFactory.getConnector().subscribe("Update", jobsUri,
  +    					0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY,
  +						new Subscriber() {
  +    				public void notify(URI uri, Map information) {
  +    					update(uri);
  +    				}
  +    			}, Constants.CREDENTIALS);
  +    		} else {
  +    			logger.log(Level.INFO, "Configured jobs resource '"+jobsUri+"' not found!");
  +    		}
  +    		jobs.addAll(applicationJobs.values());
  +            installedJobs.put(jobsUri, applicationJobs.keySet());
  +        } catch (Exception exception) {
  +            logger.log(Level.SEVERE, "Error while parsing messages", exception);
  +        }
  +	}
  +	
  +	public void uninstall(URI jobsUri) {
  +        logger.log(Level.INFO, "Uninstalling jobs '"+jobsUri+"'");
  +		Collection jobKeys = (Collection)installedJobs.get(jobs);
  +		for ( Iterator i = jobKeys.iterator(); i.hasNext(); ) {
  +			String jobKey = (String)i.next();
  +			jobs.remove(jobKey);
  +            logger.log(Level.INFO, "Removing job '"+jobKey+"'");
  +		}
  +		installedJobs.remove(jobsUri);
  +	}
  +
  +	public void update(URI jobsUri) {
  +		uninstall(jobsUri);
  +		install(jobsUri);
  +	}	
  +	
       /**
   	 * @return Returns the timer.
   	 */
  @@ -93,7 +143,7 @@
   		return timer;
   	}
   
  -    public void notify(Map information) {
  +    public void notify(URI uri, Map information) {
           logger.log(Level.INFO, "Scheduler received map='"+information+"'");
           synchronized( jobs) {
               for ( Iterator i = jobs.iterator(); i.hasNext(); ) {
  
  
  
  1.2       +7 -3      jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ApplicationListener.java
  
  Index: ApplicationListener.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ApplicationListener.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- ApplicationListener.java	12 May 2004 17:20:20 -0000	1.1
  +++ ApplicationListener.java	13 May 2004 13:30:52 -0000	1.2
  @@ -1,7 +1,11 @@
   package org.apache.slide.projector.engine;
   
  +import org.apache.slide.projector.URI;
  +
   public interface ApplicationListener {
  -	public void install(Application application);
  +	public void install(String type, URI configuration);
   	
  -	public void uninstall(Application application);
  -}
  +	public void uninstall(String type, URI configuration);
  +
  +	public void update(String type, URI configuration);
  +}
  \ No newline at end of file
  
  
  
  1.5       +54 -38    jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ProcessorManager.java
  
  Index: ProcessorManager.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ProcessorManager.java,v
  retrieving revision 1.4
  retrieving revision 1.5
  diff -u -r1.4 -r1.5
  --- ProcessorManager.java	12 May 2004 17:20:20 -0000	1.4
  +++ ProcessorManager.java	13 May 2004 13:30:52 -0000	1.5
  @@ -31,7 +31,7 @@
    * They are reloaded if an event occurs that indicates, that the class or configuration has changed
    * or was updated.
    */
  -public class ProcessorManager implements ApplicationListener {
  +public class ProcessorManager implements ApplicationListener, Subscriber {
       public final static URI BINARY = new URIResource("/image");
       public final static URI LOCALE_RESOLVER = new URIResource("/localeResolver");
       public final static URI URL = new URIResource("/url");
  @@ -51,53 +51,69 @@
       private ProcessorManager() {
       }
       	
  -    public void install(final Application application) {
  -        logger.log(Level.INFO, "Installing processors of application '"+application.getApplicationUri()+"'");
  +    public void install(String type, URI configurationUri) {
  +    	if ( type == Application.PROCESSORS ) {
  +    		install(configurationUri);
  +    	}
  +    }
  +    
  +    public void uninstall(String type, URI configurationUri) {
  +    	if ( type == Application.PROCESSORS ) {
  +    		uninstall(configurationUri);
  +    	}
  +    }
  +    
  +    public void update(String type, URI configurationUri) {
  +    	if ( type == Application.PROCESSORS ) {
  +    		update(configurationUri);
  +    	}
  +    }
  +    
  +    private void install(final URI configurationUri) {
  +    	logger.log(Level.INFO, "Installing processors '"+configurationUri+"'");
       	try {
  -    		List processorConfigurations = application.getProcessors();
  -    		for ( Iterator i = processorConfigurations.iterator(); i.hasNext(); ) {
  -            	List processors = new ArrayList();
  -    			URI configurationUri = (URI)i.next();
  -    			InputStream configuration = ((StreamableResource)ConnectorFactory.getConnector().getResource(configurationUri, Constants.CREDENTIALS)).getInputStream();
  -    			SimpleImporter importer = new SimpleImporter();
  -    			ConfigurationHandler handler = new ConfigurationHandler(processors);
  -    			importer.addSimpleImportHandler(handler);
  -    			importer.parse(new InputSource(configuration));
  -        		installedProcessors.put(configurationUri, processors);
  -		        ConnectorFactory.getConnector().subscribe("Update", configurationUri.toString(), 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY,
  -		                new Subscriber() {
  -		                    public void notify(Map information) {
  -								uninstall(application);
  -								install(application);
  -		                    }
  -		                }, Constants.CREDENTIALS);
  -    		}
  +    		List processors = new ArrayList();
  +    		InputStream configuration = ((StreamableResource)ConnectorFactory.getConnector().getResource(configurationUri, Constants.CREDENTIALS)).getInputStream();
  +    		SimpleImporter importer = new SimpleImporter();
  +    		ConfigurationHandler handler = new ConfigurationHandler(processors);
  +    		importer.addSimpleImportHandler(handler);
  +    		importer.parse(new InputSource(configuration));
  +    		installedProcessors.put(configurationUri, processors);
  +    		ConnectorFactory.getConnector().subscribe("Update", configurationUri, 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, this, Constants.CREDENTIALS);
       	} catch (Exception exception) {
       		logger.log(Level.SEVERE, "Error while parsing configuration", exception);
       	}
       }
  -    
  -    public void uninstall(Application application) {
  -        logger.log(Level.INFO, "Uninstalling processors of application '"+application.getApplicationUri()+"'");
  -    	for ( Iterator i = application.getProcessors().iterator(); i.hasNext(); ) {
  -    		URI processorsUri = (URI)i.next();
  -        	List processors = (List)installedProcessors.get(processorsUri);
  -        	for ( Iterator j = processors.iterator(); j.hasNext(); ) {
  -        		URI processorUri = (URI)j.next();
  -        		processorMap.remove(processorUri);
  -        		ProcessorDescriptor processorDescriptor = getProcessorDescriptor(processorUri); 
  -        		processorDescriptors.remove(processorDescriptor);
  -        		configuredProcessors.remove(processorDescriptor.getConfiguration());
  -        		logger.log(Level.INFO, "Removing processor: "+processorUri);
  -        	}
  +
  +    public void uninstall(URI configurationUri) {
  +    	logger.log(Level.INFO, "Uninstalling processors '"+configurationUri+"'");
  +    	List processors = (List)installedProcessors.get(configurationUri);
  +    	for ( Iterator j = processors.iterator(); j.hasNext(); ) {
  +    		URI processorUri = (URI)j.next();
  +    		processorMap.remove(processorUri);
  +    		ProcessorDescriptor processorDescriptor = getProcessorDescriptor(processorUri); 
  +    		processorDescriptors.remove(processorDescriptor);
  +    		configuredProcessors.remove(processorDescriptor.getConfiguration());
  +    		logger.log(Level.INFO, "Removing processor: "+processorUri);
       	}
  +		installedProcessors.remove(configurationUri);
  +		ConnectorFactory.getConnector().unsubscribe(configurationUri, this, Constants.CREDENTIALS);
  +    }
  +    
  +    private void update(final URI configurationUri) {
  +    	uninstall(configurationUri);
  +    	install(configurationUri);
       }
       
       public static ProcessorManager getInstance() {
           return processorManager;
       }
   
  -    public Processor getProcessor(URI uri) throws ProcessException {
  +	public void notify(URI uri, Map information) {
  +		update(uri);
  +	}
  +
  +	public Processor getProcessor(URI uri) throws ProcessException {
           if ( processorMap.containsKey(uri) ) {
               return (Processor)processorMap.get(uri);
           }
  @@ -254,9 +270,9 @@
                           StreamableResource config = (StreamableResource)ConnectorFactory.getConnector().getResource(new URIResource(Constants.REPOSITORY_DOMAIN+configURI), Constants.CREDENTIALS);
                           ((ConfigurableProcessor)processor).configure(config);
                           // listen for configuration changes
  -                        ConnectorFactory.getConnector().subscribe("Update", Constants.REPOSITORY_DOMAIN+configURI, 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY,
  +                        ConnectorFactory.getConnector().subscribe("Update", new URIResource(Constants.REPOSITORY_DOMAIN+configURI), 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY,
                                   new Subscriber() {
  -                                    public void notify(Map information) {
  +                                    public void notify(URI uri, Map information) {
                                           logger.log(Level.INFO, "Reloading processor with URI='"+uri+"', configuration URI='"+configURI+"'");
                                           try {
                                               StreamableResource config = (StreamableResource)ConnectorFactory.getConnector().getResource(new URIResource(Constants.REPOSITORY_DOMAIN+configURI), Constants.CREDENTIALS);
  
  
  
  1.2       +27 -36    jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/Application.java
  
  Index: Application.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/Application.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- Application.java	12 May 2004 17:20:20 -0000	1.1
  +++ Application.java	13 May 2004 13:30:52 -0000	1.2
  @@ -1,29 +1,27 @@
  -/*
  - * Created on 12.05.2004
  - *
  - * TODO To change the template for this generated file go to
  - * Window - Preferences - Java - Code Generation - Code and Comments
  - */
   package org.apache.slide.projector.engine;
   
   import java.util.ArrayList;
  +import java.util.HashMap;
   import java.util.List;
  +import java.util.Map;
   
   import org.apache.slide.projector.URI;
   
   public final class Application {
  -	private URI applicationUri;
  +	public final static String PROCESSORS = "processors";
  +	public final static String MESSAGES = "messages";
  +	public final static String JOBS = "jobs";
  +	
  +	private URI uri;
   	private String displayName, vendor, description;
  -	private List processors = new ArrayList();
  -	private List messages = new ArrayList(); 
  -	private List jobs = new ArrayList();
  +	private Map content = new HashMap();
   
   	Application(URI applicationUri) {
  -		this.applicationUri = applicationUri;
  +		this.uri = applicationUri;
   	}
   	
  -	public URI getApplicationUri() {
  -		return applicationUri;
  +	public URI getUri() {
  +		return uri;
   	}
   	
   	String getDescription() {
  @@ -41,36 +39,29 @@
   	void setDisplayName(String displayName) {
   		this.displayName = displayName;
   	}
  -
  -	void addJobs(URI jobsUri) {
  -		jobs.add(jobsUri);
  -	}
  -
  -	List getJobs() {
  -		return jobs;
  -	}
  -
  -	void addMessages(URI messagesUri) {
  -		messages.add(messagesUri);
  -	}
  -
  -	public List getMessages() {
  -		return messages;
  +	
  +	String getVendor() {
  +		return vendor;
   	}
   
  -	void addProcessors(URI processorsUri) {
  -		processors.add(processorsUri);
  +	void setVendor(String vendor) {
  +		this.vendor = vendor;
   	}
   
  -	List getProcessors() {
  -		return processors;
  +	void addContent(String type, URI contentUri) {
  +		List contentUris = (List)content.get(type);
  +		if ( contentUris == null ) {
  +			contentUris = new ArrayList();
  +			content.put(type, contentUris);
  +		}
  +		contentUris.add(contentUri);
   	}
   
  -	String getVendor() {
  -		return vendor;
  +	List getContent(String type) {
  +		return (List)content.get(type);
   	}
   
  -	void setVendor(String vendor) {
  -		this.vendor = vendor;
  +	Map getContent() {
  +		return content;
   	}
   }
  
  
  
  1.2       +126 -87   jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ApplicationManager.java
  
  Index: ApplicationManager.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/engine/ApplicationManager.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- ApplicationManager.java	12 May 2004 17:20:20 -0000	1.1
  +++ ApplicationManager.java	13 May 2004 13:30:52 -0000	1.2
  @@ -27,76 +27,58 @@
       private final static Logger logger = Logger.getLogger(ApplicationManager.class.getName());
   
       private final static String APPLICATION_CONFIG = "application.xml";
  +    private final static Context context = new SystemContext();
   
       private static ApplicationManager applicationManager;
       private List applicationListeners = new ArrayList();
  -    private List applications = new ArrayList();
  +    private Map installedApplications = new HashMap(); // URI -> Application
       
       private ApplicationManager() {
           logger.log(Level.INFO, "Starting projector...");
  -    	ConnectorFactory.getConnector().subscribe("Update/newmember", Constants.APPLICATIONS_DIR, 1, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, 
  +    	ConnectorFactory.getConnector().subscribe("Update/newmember", new URIResource(Constants.APPLICATIONS_DIR), 1, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, 
       			new Subscriber() {
  -    		public void notify(Map information) {
  +    		public void notify(URI uri, Map information) {
       			logger.log(Level.INFO, "Package manager received add event");
  -    			applicationManager.configure();
  +    			applicationManager.installApplications();
       		}
  -    	}, Constants.CREDENTIALS);
  -    	ConnectorFactory.getConnector().subscribe("Delete", Constants.APPLICATIONS_DIR, 1, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, 
  +    	}, context.getCredentials());
  +    	ConnectorFactory.getConnector().subscribe("Delete", new URIResource(Constants.APPLICATIONS_DIR), 1, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, 
       			new Subscriber() {
  -    		public void notify(Map information) {
  +    		public void notify(URI uri, Map information) {
       			logger.log(Level.INFO, "Package manager received delete event");
  -    			applicationManager.configure();
  +    			applicationManager.installApplications();
       		}
  -    	}, Constants.CREDENTIALS);
  +    	}, context.getCredentials());
       	applicationListeners.add(ProcessorManager.getInstance());
       	applicationListeners.add(MessageManager.getInstance());
  -    	configure();
  +    	installApplications();
       }
   
  -	private synchronized void configure() {
  -		final Context context = new SystemContext();
  -        logger.log(Level.INFO, "Parsing application configurations");
  -			Resource[] applicationUris;
  -			try {
  -				List removedApplications = new ArrayList();
  -				removedApplications.addAll(applications);
  -				applicationUris = ((ArrayResource)ConnectorFactory.getConnector().getChildren(new URIResource(Constants.APPLICATIONS_DIR), context.getCredentials())).getArray();
  -				for ( int i = 0; i < applicationUris.length; i++ ) {
  -					URI applicationUri = new URIResource(applicationUris[i]+"/"); 
  -					if ( !isApplicationInstalled(applicationUri) ) {
  -						SimpleImporter importer = new SimpleImporter();
  -						URI applicationDefinition = new URIResource(applicationUri.toString()+APPLICATION_CONFIG);
  -						StreamableResource applicationDefinitionResouce = ((StreamableResource)ConnectorFactory.getConnector().getResource(applicationDefinition, context.getCredentials())); 
  -						if ( applicationDefinitionResouce != null ) {
  -							try {
  -								InputStream configuration = applicationDefinitionResouce.getInputStream();
  -								ConfigurationHandler handler = new ConfigurationHandler(applicationUri);
  -								importer.addSimpleImportHandler(handler);
  -								importer.parse(new InputSource(configuration));
  -								Application installedApplication = handler.getApplication(); 
  -								install(installedApplication);
  -							} catch (ParserConfigurationException e) {
  -								logger.log(Level.SEVERE, "Exception while parsing application configuration. Skipping installation...", e);
  -							} catch (SAXException e) {
  -								logger.log(Level.SEVERE, "Exception while parsing application configuration. Skipping installation...", e);
  -							}				
  -						} else {
  -							logger.log(Level.SEVERE, "Application definition (application.xml) not found in directory '"+applicationUri+"'. Application will not be installed!");
  -						}
  -					} else {
  -				        logger.log(Level.INFO, "Application '"+applicationUri+"' already installed");
  -						removedApplications.remove(getApplication(removedApplications, applicationUri));
  -					}
  -				}  
  -				for ( Iterator i = removedApplications.iterator(); i.hasNext(); ) {
  -					Application removedApplication = (Application)i.next();
  -					uninstall(removedApplication);
  -				}
  -			} catch (IOException e) {
  -				logger.log(Level.SEVERE, "Could not determine installed applications!", e);
  -			}
  -	}	
  -
  +    private synchronized void installApplications() {
  +    	Resource[] applicationUris;
  +    	try {
  +    		List removedApplications = new ArrayList();
  +    		removedApplications.addAll(installedApplications.keySet());
  +    		applicationUris = ((ArrayResource)ConnectorFactory.getConnector().getChildren(new URIResource(Constants.APPLICATIONS_DIR), context.getCredentials())).getArray();
  +    		for ( int i = 0; i < applicationUris.length; i++ ) {
  +    			URI applicationUri = new URIResource(applicationUris[i]+"/"); 
  +    			if ( !installedApplications.containsKey(applicationUri) ) {
  +    				Application installedApplication = parseApplication(applicationUri);
  +    				if ( installedApplication != null ) install(installedApplication);
  +    			} else {
  +    				logger.log(Level.INFO, "Application '"+applicationUri+"' already installed");
  +    				removedApplications.remove(applicationUri);
  +    			}
  +    		}  
  +    		for ( Iterator i = removedApplications.iterator(); i.hasNext(); ) {
  +    			Application removedApplication = (Application)installedApplications.get((URI)i.next());
  +    			uninstall(removedApplication);
  +    		}
  +    	} catch (IOException e) {
  +    		logger.log(Level.SEVERE, "Could not determine installed applications!", e);
  +    	}
  +    }	
  +    
       public static ApplicationManager getInstance() {
       	if ( applicationManager == null ) {
       		applicationManager = new ApplicationManager(); 
  @@ -104,51 +86,108 @@
           return applicationManager;
       }
       
  +    private Application parseApplication(URI applicationUri) {
  +    	try {
  +    		SimpleImporter importer = new SimpleImporter();
  +    		URI applicationDefinition = new URIResource(applicationUri.toString()+APPLICATION_CONFIG);
  +    		StreamableResource applicationDefinitionResouce = ((StreamableResource)ConnectorFactory.getConnector().getResource(applicationDefinition, context.getCredentials())); 
  +    		if ( applicationDefinitionResouce != null ) {
  +    			InputStream configuration = applicationDefinitionResouce.getInputStream();
  +    			ConfigurationHandler handler = new ConfigurationHandler(applicationUri);
  +    			importer.addSimpleImportHandler(handler);
  +    			importer.parse(new InputSource(configuration));
  +    			return handler.getApplication(); 
  +    		} else {
  +    			logger.log(Level.SEVERE, "Application definition (application.xml) not found in directory '"+applicationUri+"'. Application will not be installed!");
  +    		}
  +    	} catch (ParserConfigurationException e) {
  +    		logger.log(Level.SEVERE, "Exception while parsing application configuration. Skipping installation...", e);
  +    	} catch (SAXException e) {
  +    		logger.log(Level.SEVERE, "Exception while parsing application configuration. Skipping installation...", e);
  +    	} catch (IOException e) {
  +    		logger.log(Level.SEVERE, "Could not get application information. Skipping installation...", e);
  +		}				
  +		return null;
  +    }
  +    
       private Application getApplication(List applications, URI applicationUri) {
       	for ( Iterator i = applications.iterator(); i.hasNext(); ) {
       		Application application = (Application)i.next();
  -    		if ( application.getApplicationUri().equals(applicationUri) ) return application; 
  +    		if ( application.getUri().equals(applicationUri) ) return application; 
       	}
       	return null;
       }
       
  -    private boolean isApplicationInstalled(URI applicationUri) {
  -    	for ( Iterator i = applications.iterator(); i.hasNext(); ) {
  -    		if ( ((Application)i.next()).getApplicationUri().equals(applicationUri) ) return true;
  -    	}
  -    	return false;
  -    }
  -	
  +	private synchronized void updateApplication(URI applicationUri) {
  +        logger.log(Level.INFO, "Updating application '"+applicationUri+"'");
  +        // Compare newly parsed application with previously installed and send diffs
  +        Application installedApplication = (Application)installedApplications.get(applicationUri);
  +        Application updatedApplication = parseApplication(applicationUri);
  +        for ( Iterator i = installedApplication.getContent().entrySet().iterator(); i.hasNext(); ) {
  +        	Map.Entry entry = (Map.Entry)i.next();
  +            List removed = new ArrayList();
  +            removed.addAll((List)entry.getValue());
  +            List updated = updatedApplication.getContent((String)entry.getKey());
  +            if ( updated != null ) {
  +            	removed.removeAll(updated);
  +            }
  +    		for ( Iterator j = removed.iterator(); j.hasNext(); ) {
  +    			for ( Iterator k = applicationListeners.iterator(); k.hasNext(); ) {
  +    				((ApplicationListener)k.next()).uninstall((String)entry.getKey(), (URI)j.next());
  +    			}
  +    		}
  +        }
  +        for ( Iterator i = updatedApplication.getContent().entrySet().iterator(); i.hasNext(); ) {
  +        	Map.Entry entry = (Map.Entry)i.next();
  +            List added = new ArrayList();
  +            added.addAll((List)entry.getValue());
  +            List installed = installedApplication.getContent((String)entry.getKey());
  +            if ( installed != null ) {
  +            	added.removeAll(installed);
  +            }
  +    		for ( Iterator j = added.iterator(); j.hasNext(); ) {
  +    			for ( Iterator k = applicationListeners.iterator(); k.hasNext(); ) {
  +    				((ApplicationListener)k.next()).install((String)entry.getKey(), (URI)j.next());
  +    			}
  +    		}
  +        }
  +	}	
  +
   	private void install(Application application) {
  -        logger.log(Level.INFO, "Install application '"+application.getApplicationUri()+"'");
  -		for ( Iterator i = applicationListeners.iterator(); i.hasNext(); ) {
  -			((ApplicationListener)i.next()).install(application);
  +        logger.log(Level.INFO, "Installing application '"+application.getUri()+"'");
  +    	ConnectorFactory.getConnector().subscribe("Update", application.getUri(), 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, 
  +    			new Subscriber() {
  +    		public void notify(URI uri, Map information) {
  +    			applicationManager.updateApplication(uri);
  +    		}
  +    	}, context.getCredentials());
  +		for ( Iterator i = application.getContent().entrySet().iterator(); i.hasNext(); ) {
  +			Map.Entry entry = (Map.Entry)i.next();
  +			for ( Iterator j = ((List)entry.getValue()).iterator(); j.hasNext(); ) {
  +				URI uri = (URI)j.next();
  +				for ( Iterator k = applicationListeners.iterator(); k.hasNext(); ) {
  +					((ApplicationListener)k.next()).install((String)entry.getKey(), uri);
  +				}
  +			}
   		}
  -		applications.add(application);
  +		installedApplications.put(application.getUri(), application);
   	}
   	
   	private void uninstall(Application application) {
  -        logger.log(Level.INFO, "Uninstall application '"+application.getApplicationUri()+"'");
  -		for ( Iterator i = applicationListeners.iterator(); i.hasNext(); ) {
  -			((ApplicationListener)i.next()).uninstall(application);
  +        logger.log(Level.INFO, "Uninstall application '"+application.getUri()+"'");
  +        // FIXME: Unsubscribe application listeners
  +		for ( Iterator i = application.getContent().entrySet().iterator(); i.hasNext(); ) {
  +			Map.Entry entry = (Map.Entry)i.next();
  +			for ( Iterator j = ((List)entry.getValue()).iterator(); j.hasNext(); ) {
  +				URI uri = (URI)j.next();
  +				for ( Iterator k = applicationListeners.iterator(); k.hasNext(); ) {
  +					((ApplicationListener)k.next()).uninstall((String)entry.getKey(), uri);
  +				}
  +			}
   		}
  -		applications.remove(applications.indexOf(application));
  +		installedApplications.remove(application.getUri());
   	}
   	
  -	private void update(Application application) {
  -		uninstall(application);
  -		install(application);
  -	}
  -    
  -    public List getProcessorConfigurations() {
  -    	List processorConfigurations = new ArrayList();
  -    	for ( Iterator i = applications.iterator(); i.hasNext(); ) {
  -    		Application application = (Application)i.next();
  -        	processorConfigurations.addAll(application.getProcessors());
  -    	}
  -    	return processorConfigurations;
  -    }
  -    
       static private final class ConfigurationHandler extends DefaultSimpleImportHandler {
   		private Application application;
   		private URI applicationUri;
  @@ -172,11 +211,11 @@
   				application.setDescription(leadingCDdata);			
               } else if ( path.matches("content/processors") ) {
               	String uri = attributes.getValue("uri"); 
  -            	application.addProcessors(new URIResource(applicationUri+uri));			
  +            	application.addContent(Application.PROCESSORS, new URIResource(applicationUri+attributes.getValue("uri")));			
               } else if ( path.matches("content/messages") ) {
  -				application.addMessages(new URIResource(applicationUri+attributes.getValue("uri")));			
  +            	application.addContent(Application.MESSAGES, new URIResource(applicationUri+attributes.getValue("uri")));			
               } else if ( path.matches("content/jobs") ) {
  -				application.addJobs(new URIResource(applicationUri+attributes.getValue("uri")));			
  +            	application.addContent(Application.JOBS, new URIResource(applicationUri+attributes.getValue("uri")));			
               }
           }
       }
  
  
  
  1.3       +60 -42    jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/i18n/MessageManager.java
  
  Index: MessageManager.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/i18n/MessageManager.java,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- MessageManager.java	12 May 2004 17:20:20 -0000	1.2
  +++ MessageManager.java	13 May 2004 13:30:52 -0000	1.3
  @@ -18,13 +18,12 @@
   import java.util.Collection;
   import java.util.HashMap;
   import java.util.Iterator;
  -import java.util.List;
   import java.util.Locale;
   import java.util.Map;
   import java.util.logging.Level;
   import java.util.logging.Logger;
   
  -public class MessageManager implements ApplicationListener {
  +public class MessageManager implements ApplicationListener, Subscriber {
       private static Logger logger = Logger.getLogger(MessageManager.class.getName());
   
       private final static String MESSAGES_CONFIG = "messages.xml";
  @@ -41,7 +40,7 @@
       public static MessageManager getInstance() {
       	return messageManager;
       }
  -    
  +
       public static String getText(String id, String entry, Object[] arguments, Locale locale, String defaultText) {
           Message message = messageManager.findMessage(id, locale);
           if (message != null) return messageManager.format(message.getEntry(entry), arguments);
  @@ -60,53 +59,72 @@
           return message.getEntries();
       }
   
  -	public void install(final Application application) {
  -        logger.log(Level.INFO, "Installing messages of application '"+application.getApplicationUri()+"'");
  -        try {
  -        	List messageConfigurations = application.getMessages();
  -        	Map applicationMessages = new HashMap();
  -        	for ( Iterator i = messageConfigurations.iterator(); i.hasNext(); ) {
  -        		URI messagesUri = (URI)i.next();
  -        		StreamableResource messagesResource = (StreamableResource)ConnectorFactory.getConnector().getResource(messagesUri, Constants.CREDENTIALS);
  -        		if ( messagesResource != null ) {
  -        			InputStream inputStream = messagesResource.getInputStream();
  -        			SimpleImporter importer = new SimpleImporter();
  -        			importer.setIncludeLeadingCDataIntoStartElementCallback(true);
  -        			ConfigurationHandler handler = new ConfigurationHandler();
  -        			importer.addSimpleImportHandler(handler);
  -        			importer.parse(new InputSource(inputStream));
  -        			Map parsedMessages = handler.getMessages();
  -        			applicationMessages.putAll(parsedMessages);
  -        			ConnectorFactory.getConnector().subscribe("Update", messagesUri.toString(),
  -        					0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY,
  -							new Subscriber() {
  -        				public void notify(Map information) {
  -        					uninstall(application);
  -        					install(application);
  -        				}
  -        			}, Constants.CREDENTIALS);
  -        		} else {
  -                    logger.log(Level.INFO, "Configured messages resource '"+messagesUri+"' not found!");
  -        		}
  -        	}
  -            messages.putAll(applicationMessages);
  -            installedMessages.put(application.getApplicationUri(), applicationMessages.keySet());
  -        } catch (Exception exception) {
  -            logger.log(Level.SEVERE, "Error while parsing messages", exception);
  -        }
  -	}
  +    public void install(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		install(configurationUri);
  +    	}
  +    }
  +    
  +    public void uninstall(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		uninstall(configurationUri);
  +    	}
  +    }
  +    
  +    public void update(String type, URI configurationUri) {
  +    	if ( type == Application.MESSAGES ) {
  +    		update(configurationUri);
  +    	}
  +    }
  +    
  +    public void install(URI messagesUri) {
  +    	logger.log(Level.INFO, "Installing messages '"+messagesUri+"'");
  +    	try {
  +    		Map applicationMessages = new HashMap();
  +    		StreamableResource messagesResource = (StreamableResource)ConnectorFactory.getConnector().getResource(messagesUri, Constants.CREDENTIALS);
  +    		if ( messagesResource != null ) {
  +    			InputStream inputStream = messagesResource.getInputStream();
  +    			SimpleImporter importer = new SimpleImporter();
  +    			importer.setIncludeLeadingCDataIntoStartElementCallback(true);
  +    			ConfigurationHandler handler = new ConfigurationHandler();
  +    			importer.addSimpleImportHandler(handler);
  +    			importer.parse(new InputSource(inputStream));
  +    			Map parsedMessages = handler.getMessages();
  +    			applicationMessages.putAll(parsedMessages);
  +    			ConnectorFactory.getConnector().subscribe("Update", messagesUri, 0, Constants.SUBSCRIPTION_LIFETIME, Constants.NOTIFICATION_DELAY, this, Constants.CREDENTIALS);
  +    		} else {
  +    			logger.log(Level.INFO, "Configured messages resource '"+messagesUri+"' not found!");
  +    		}
  +    		messages.putAll(applicationMessages);
  +    		installedMessages.put(messagesUri, applicationMessages.keySet());
  +    	} catch (Exception exception) {
  +    		logger.log(Level.SEVERE, "Error while parsing messages", exception);
  +    	}
  +    }
   	
  -	public void uninstall(Application application) {
  -        logger.log(Level.INFO, "Uninstalling messages of application '"+application.getApplicationUri()+"'");
  -		Collection messageKeys = (Collection)installedMessages.get(application.getApplicationUri());
  +	public void uninstall(URI messageUri) {
  +        logger.log(Level.INFO, "Uninstalling messages '"+messageUri+"'");
  +		Collection messageKeys = (Collection)installedMessages.get(messageUri);
   		for ( Iterator i = messageKeys.iterator(); i.hasNext(); ) {
   			String messageKey = (String)i.next();
   			messages.remove(messageKey);
               logger.log(Level.INFO, "Removing message with key '"+messageKey+"'");
   		}
  +		installedMessages.remove(messageUri);
  +		ConnectorFactory.getConnector().unsubscribe(messageUri, this, Constants.CREDENTIALS);
   	}
       
  -    private String format(String formatString, Object[] arguments) {
  +    public void update(URI messagesUri) {
  +    	uninstall(messagesUri);
  +    	install(messagesUri);
  +    }
  +    	
  +	public void notify(URI uri, Map information) {
  +		uninstall(uri);
  +		install(uri);
  +	}
  +
  +	private String format(String formatString, Object[] arguments) {
           if (formatString == null) return null;
           return MessageFormat.format(formatString, arguments);
       }
  
  
  
  1.2       +58 -11    jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/webdav/WebdavDispatcher.java
  
  Index: WebdavDispatcher.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/webdav/WebdavDispatcher.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- WebdavDispatcher.java	3 May 2004 14:20:27 -0000	1.1
  +++ WebdavDispatcher.java	13 May 2004 13:30:52 -0000	1.2
  @@ -33,6 +33,7 @@
   import org.apache.commons.httpclient.protocol.Protocol;
   import org.apache.commons.httpclient.methods.PutMethod;
   import org.apache.slide.projector.Constants;
  +import org.apache.slide.projector.URI;
   import org.apache.slide.projector.connector.Subscriber;
   import org.apache.util.XMLPrinter;
   import org.apache.webdav.lib.methods.XMLResponseMethodBase;
  @@ -121,8 +122,8 @@
           timer.schedule(poll, pollInterval, pollInterval);
       }
   
  -    public void subscribe(String method, String uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials) {
  -        SubscribeMethod subscribeMethod = new SubscribeMethod(uri);
  +    public void subscribe(String method, URI uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials) {
  +        SubscribeMethod subscribeMethod = new SubscribeMethod(uri.toString());
           subscribeMethod.addRequestHeader(SubscribeMethod.H_NOTIFICATION_TYPE, method);
           subscribeMethod.addRequestHeader(SubscribeMethod.H_CALL_BACK, "httpu://"+notificationHost+":"+notificationPort);
           subscribeMethod.addRequestHeader(SubscribeMethod.H_NOTIFICATION_DELAY, String.valueOf(notificationDelay));
  @@ -137,7 +138,7 @@
                   String subscriptionId = subscribeMethod.getResponseHeader(SubscribeMethod.H_SUBSCRIPTION_ID).getValue();
                   logger.log(Level.INFO, "Received subscription id="+subscriptionId+", listener: "+listener);
                   int id = Integer.valueOf(subscriptionId).intValue();
  -                subscribers.add(new Subscription(id, listener));
  +                subscribers.add(new Subscription(id, uri, listener));
                   if ( subscribersAsString == null ) {
                       subscribersAsString = String.valueOf(id);
                   } else {
  @@ -151,6 +152,32 @@
           }
       }
   
  +    public void unsubscribe(URI uri, Subscriber listener, Credentials credentials) {
  +        UnsubscribeMethod unsubscribeMethod = new UnsubscribeMethod(uri.toString());
  +		for ( Iterator i = subscribers.iterator(); i.hasNext(); ) {
  +			Subscription subscription = (Subscription)i.next();
  +			if ( subscription.getSubscriber().equals(listener) ) {
  +				String id = String.valueOf(subscription.getId());
  +				unsubscribeMethod.addRequestHeader(UnsubscribeMethod.H_SUBSCRIPTION_ID, id);
  +				try {
  +					unsubscribeMethod.setDoAuthentication(true);
  +					HttpState httpState = new HttpState();
  +					httpState.setCredentials(null, repositoryHost, credentials);
  +					int state = unsubscribeMethod.execute(httpState, new HttpConnection(repositoryHost, repositoryPort, protocol));
  +					if ( state == HttpStatus.SC_OK ) {
  +						i.remove();
  +						return;
  +					} else {
  +						logger.log(Level.SEVERE, "Unsubscription failed. State: "+state);
  +					}
  +				} catch (IOException e) {
  +					logger.log(Level.SEVERE, "Unsubscription of listener '"+listener+"' failed!", e);
  +				}
  +			}
  +		}
  +		logger.log(Level.SEVERE, "Listener not subscribed!");
  +    }
  +
       public void fireEvent(Map information, Credentials credentials) throws IOException  {
           EventMethod eventMethod = new EventMethod(repositoryDomain);
           eventMethod.addEvent(new Event(information));
  @@ -279,17 +306,23 @@
   
       private class Subscription {
           private int id;
  -        private Subscriber eventListener;
  +		private URI uri;
  +        private Subscriber subscriber;
   
  -        public Subscription(int id, Subscriber eventListener) {
  +        public Subscription(int id, URI uri, Subscriber subscriber) {
               this.id = id;
  -            this.eventListener = eventListener;
  +            this.uri = uri;
  +            this.subscriber = subscriber;
           }
   
           public void fireEvent(Map information) {
  -            eventListener.notify(information);
  +            subscriber.notify(uri, information);
           }
  -
  +	
  +		public Subscriber getSubscriber() {
  +			return subscriber;
  +		}
  +			
           public int getId() {
               return id;
           }
  @@ -406,6 +439,20 @@
           public final static String H_DEPTH = "Depth";
           
           public SubscribeMethod(String uri) {
  +            super(uri);
  +        }
  +
  +        public String getName() {
  +            return NAME;
  +        }
  +    }
  +
  +    private class UnsubscribeMethod extends PutMethod {
  +        public static final String NAME = "UNSUBSCRIBE";
  +
  +        public final static String H_SUBSCRIPTION_ID = "Subscription-id";
  +        
  +        public UnsubscribeMethod(String uri) {
               super(uri);
           }
   
  
  
  
  1.3       +5 -1      jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/webdav/WebdavConnector.java
  
  Index: WebdavConnector.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/webdav/WebdavConnector.java,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- WebdavConnector.java	11 May 2004 15:23:43 -0000	1.2
  +++ WebdavConnector.java	13 May 2004 13:30:52 -0000	1.3
  @@ -123,8 +123,12 @@
           return new ArrayResource((Resource[])children.toArray(new Resource[children.size()]));
       }
       
  -    public void subscribe(String method, String uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials) {
  +    public void subscribe(String method, URI uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials) {
           dispatcher.subscribe(method, uri, depth, lifetime, notificationDelay, listener, credentials);
  +    }
  +    
  +    public void unsubscribe(URI uri, Subscriber listener, Credentials credentials) {
  +        dispatcher.unsubscribe(uri, listener, credentials);
       }
   
       public void fireEvent(Map information, Credentials credentials) throws IOException {
  
  
  
  1.3       +3 -1      jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/Connector.java
  
  Index: Connector.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/Connector.java,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- Connector.java	11 May 2004 15:23:43 -0000	1.2
  +++ Connector.java	13 May 2004 13:30:52 -0000	1.3
  @@ -28,7 +28,9 @@
       
       public Resource[] search(String query, Credentials credentials) throws IOException;
   
  -    public void subscribe(String method, String uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials);
  +    public void subscribe(String method, URI uri, int depth, int lifetime, int notificationDelay, Subscriber listener, Credentials credentials);
  +
  +    public void unsubscribe(URI uri, Subscriber listener, Credentials credentials);
   
       public void fireEvent(Map information, Credentials credentials) throws IOException;
   
  
  
  
  1.2       +6 -4      jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/Subscriber.java
  
  Index: Subscriber.java
  ===================================================================
  RCS file: /home/cvs/jakarta-slide/proposals/projector/src/java/org/apache/slide/projector/connector/Subscriber.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- Subscriber.java	3 May 2004 14:20:29 -0000	1.1
  +++ Subscriber.java	13 May 2004 13:30:52 -0000	1.2
  @@ -25,6 +25,8 @@
   
   import java.util.Map;
   
  +import org.apache.slide.projector.URI;
  +
   /**
    * The EventListener interface
    * 
  @@ -35,5 +37,5 @@
       public final static String SOURCE_URI = "source-uri";
       public final static String TARGET_URI = "target-uri";
   
  -    public void notify(Map information);
  +    public void notify(URI uri, Map information);
   }
  
  
  

---------------------------------------------------------------------
To unsubscribe, e-mail: slide-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: slide-dev-help@jakarta.apache.org