FileDocCategorySizeDatePackage
ShareManagerImpl.javaAPI DocAzureus 3.0.3.419964Mon May 21 15:17:36 BST 2007org.gudy.azureus2.pluginsimpl.local.sharing

ShareManagerImpl

public class ShareManagerImpl extends Object implements ShareManager, ParameterListener, AEDiagnosticsEvidenceGenerator, TOTorrentProgressListener
author
parg

Fields Summary
private static final LogIDs
LOGID
public static final String
TORRENT_STORE
public static final String
TORRENT_SUBSTORE
public static final int
MAX_FILES_PER_DIR
public static final int
MAX_DIRS
protected static ShareManagerImpl
singleton
private static AEMonitor
class_mon
protected AEMonitor
this_mon
protected TOTorrentCreator
to_creator
private volatile boolean
initialised
private volatile boolean
initialising
private File
share_dir
private URL[]
announce_urls
private ShareConfigImpl
config
private Map
shares
private shareScanner
current_scanner
private List
listeners
Constructors Summary
protected ShareManagerImpl()

	
	
	
	
		 
	
		COConfigurationManager.addListener(
			new COConfigurationListener()
			{
				public void
				configurationSaved()
				{
					announce_urls	= null;
				}
			});
		
		AEDiagnostics.addEvidenceGenerator( this );
	
Methods Summary
public ShareResourceDiraddDir(java.io.File dir)

		return( addDir( null, dir ));
	
public ShareResourceDiraddDir(ShareResourceDirContentsImpl parent, java.io.File dir)

		if (Logger.isEnabled())
			Logger.log(new LogEvent(LOGID, "ShareManager: addDir '" + dir.toString()
					+ "'"));

		try{
			this_mon.enter();
			
			return( (ShareResourceDir)addFileOrDir( parent, dir, ShareResource.ST_DIR, false ));
			
		}catch( ShareException e ){
			
			reportError(e);
			
			throw(e);
			
		}finally{
			
			this_mon.exit();
		}
	
public ShareResourceDirContentsaddDirContents(java.io.File dir, boolean recursive)

		if (Logger.isEnabled())
			Logger.log(new LogEvent(LOGID, "ShareManager: addDirContents '"
					+ dir.toString() + "'"));

		try{
			this_mon.enter();
			
			String	name = dir.getCanonicalFile().toString();
			
			reportCurrentTask( "Adding dir contents '" + name + "', recursive = " + recursive );
	
			ShareResource	old_resource = (ShareResource)shares.get( name );
			
			if ( old_resource != null ){
				
				old_resource.delete();
			}

			ShareResourceDirContents new_resource = new ShareResourceDirContentsImpl( this, dir, recursive );
						
			shares.put( name, new_resource );
			
			config.saveConfig();
			
			for (int i=0;i<listeners.size();i++){
				
				try{
					
					((ShareManagerListener)listeners.get(i)).resourceAdded( new_resource );
					
				}catch( Throwable e ){
					
					Debug.printStackTrace( e );
				}
			}
			
			return( new_resource );
			
		}catch( IOException e ){
			
			reportError(e);
			
			throw( new ShareException( "getCanoncialFile fails", e ));
			
		}catch( ShareException e ){
			
			reportError(e);
			
			throw(e);
			
		}finally{
			
			this_mon.exit();
		}
	
public ShareResourceFileaddFile(java.io.File file)

		return( addFile( null, file ));
	
protected ShareResourceFileaddFile(ShareResourceDirContentsImpl parent, java.io.File file)

		if (Logger.isEnabled())
			Logger.log(new LogEvent(LOGID, "ShareManager: addFile '"
					+ file.toString() + "'"));

		try{
			return( (ShareResourceFile)addFileOrDir( parent, file, ShareResource.ST_FILE, false ));
			
		}catch( ShareException e ){
			
			reportError(e);
			
			throw(e);
		}
	
protected ShareResourceaddFileOrDir(ShareResourceDirContentsImpl parent, java.io.File file, int type, boolean modified)

		try{
			this_mon.enter();
		
			String	name = file.getCanonicalFile().toString();
			
			ShareResource	old_resource = (ShareResource)shares.get(name);
			
			if ( old_resource != null ){
		
				old_resource.delete();
			}
			
			ShareResourceImpl new_resource;
			
			if ( type == ShareResource.ST_FILE ){
		
				reportCurrentTask( "Adding file '" + name + "'");
				
				new_resource = new ShareResourceFileImpl( this, parent, file );
				
			}else{
				
				reportCurrentTask( "Adding dir '" + name + "'");
				
				new_resource = new ShareResourceDirImpl( this, parent, file );
			}
			
			shares.put(name, new_resource );
			
			config.saveConfig();
			
			for (int i=0;i<listeners.size();i++){
				
				try{
					
					if ( modified ){
						
						((ShareManagerListener)listeners.get(i)).resourceModified( new_resource );
					
					}else{
						
						((ShareManagerListener)listeners.get(i)).resourceAdded( new_resource );				
					}
				}catch( Throwable e ){
					
					Debug.printStackTrace( e );
				}
			}
			
			return( new_resource );
			
		}catch( IOException e ){
			
			throw( new ShareException( "getCanoncialFile fails", e ));
			
		}finally{
			
			this_mon.exit();
		}
	
public voidaddListener(ShareManagerListener l)

		listeners.add(l);	
	
public voidcancelOperation()

		TOTorrentCreator	temp = to_creator;
		
		if ( temp != null ){
			
			temp.cancel();
		}
	
protected voidcheckConsistency()

			// copy set for iteration as consistency check can delete resource
		
		Iterator	it = new HashSet(shares.values()).iterator();
		
		while(it.hasNext()){
			
			ShareResourceImpl	resource = (ShareResourceImpl)it.next();
			
			try{
				resource.checkConsistency();
				
			}catch( ShareException e ){
				
				Debug.printStackTrace(e);
			}
		}
	
protected voiddelete(ShareResourceImpl resource)

		if (Logger.isEnabled())
			Logger.log(new LogEvent(LOGID, "ShareManager: resource '"
					+ resource.getName() + "' deleted"));
		
		try{
			this_mon.enter();
		
			shares.remove(resource.getName());
			
			resource.deleteInternal();
			
			config.saveConfig();
			
			for (int i=0;i<listeners.size();i++){
				
				try{
					
					((ShareManagerListener)listeners.get(i)).resourceDeleted( resource );
					
				}catch( Throwable e ){
					
					Debug.printStackTrace( e );
				}
			}
		}finally{
			
			this_mon.exit();
		}
	
protected voiddeleteTorrent(ShareItemImpl item)

		File	torrent_file = getTorrentFile(item);
				
		torrent_file.delete();
	
protected voiddeserialiseResource(java.util.Map map)

		try{
			ShareResourceImpl	new_resource = null;
			
			int	type = ((Long)map.get("type")).intValue();
			
			if ( 	type == ShareResource.ST_FILE ||
					type == ShareResource.ST_DIR ){
				
				new_resource = ShareResourceFileOrDirImpl.deserialiseResource( this, map, type );
				
			}else{
				
				new_resource = ShareResourceDirContentsImpl.deserialiseResource( this, map );
			}
			
			if ( new_resource != null ){
				
				ShareResourceImpl	old_resource = (ShareResourceImpl)shares.get(new_resource.getName());
				
				if ( old_resource != null ){
					
					old_resource.delete(true);
				}
				
				shares.put( new_resource.getName(), new_resource );
				
					// we delay the reporting of dir_contents until all recovery is complete so that
					// the resource reported is initialised correctly
				
				if ( type != ShareResource.ST_DIR_CONTENTS ){
					
					for (int i=0;i<listeners.size();i++){
						
						try{
						
							((ShareManagerListener)listeners.get(i)).resourceAdded( new_resource );
							
						}catch( Throwable e ){
						
							Debug.printStackTrace( e );
						}
					}
				}
			}
		}catch( Throwable e ){
			
			Debug.printStackTrace( e );
		}
	
public voidgenerate(IndentWriter writer)

		writer.println( "Shares" );
			
		try{
			writer.indent();

			ShareResource[]	shares = getShares();
			
			HashSet	share_map = new HashSet();
						
			for ( int i=0;i<shares.length;i++ ){
				
				ShareResource	share = shares[i];
									
				if ( share instanceof ShareResourceDirContents ){
					
					share_map.add( share );
					
				}else if ( share.getParent() != null ){
					
				}else{
					
					writer.println( getDebugName( share ));
				}
			}
			
			Iterator	it = share_map.iterator();
			
			TorrentManager tm = AzureusCoreFactory.getSingleton().getPluginManager().getDefaultPluginInterface().getTorrentManager();

			TorrentAttribute	category_attribute 	= tm.getAttribute( TorrentAttribute.TA_CATEGORY );
			TorrentAttribute	props_attribute 	= tm.getAttribute( TorrentAttribute.TA_SHARE_PROPERTIES );
			
			while( it.hasNext()){
				
				ShareResourceDirContents	root = (ShareResourceDirContents)it.next();
				
				String	cat 	= root.getAttribute( category_attribute );
				String	props 	= root.getAttribute( props_attribute );
				
				String	extra = cat==null?"":(",cat=" + cat );
				
				extra += props==null?"":(",props=" + props );
				
				extra += ",rec=" + root.isRecursive();
				
				writer.println( root.getName() + extra );
				
				generate( writer, root );
			}
		}finally{
			
			writer.exdent();
		}
	
protected voidgenerate(IndentWriter writer, ShareResourceDirContents node)

		try{
			writer.indent();

			ShareResource[]	kids = node.getChildren();
			
			for (int i=0;i<kids.length;i++){
				
				ShareResource	kid = kids[i];
				
				writer.println( getDebugName( kid ));
	
				if ( kid instanceof ShareResourceDirContents ){
					
					generate( writer, (ShareResourceDirContents)kid );
				}
			}
		}finally{
			
			writer.exdent();
		}
	
protected booleangetAddHashes()

		return( COConfigurationManager.getBooleanParameter( "Sharing Add Hashes" ));
	
protected java.net.URL[]getAnnounceURLs()

		if ( announce_urls == null ){
						
			String	protocol = COConfigurationManager.getStringParameter( "Sharing Protocol" );
			
			if ( protocol.equalsIgnoreCase( "DHT" )){
				
				announce_urls	= new URL[]{ TorrentUtils.getDecentralisedEmptyURL()};
				
			}else{
			
				URL[][]	tracker_url_sets = TRTrackerUtils.getAnnounceURLs();
				
				if ( tracker_url_sets.length == 0 ){
					
					throw( new ShareException( "ShareManager: Tracker must be configured"));
				}
			
				for (int i=0;i<tracker_url_sets.length;i++){
				
					URL[]	tracker_urls = tracker_url_sets[i];
			
					if ( tracker_urls[0].getProtocol().equalsIgnoreCase( protocol )){
					
						announce_urls = tracker_urls;
						
						break;
					}
				}
				
				if ( announce_urls == null ){
					
					throw( new ShareException( "ShareManager: Tracker must be configured for protocol '" + protocol + "'" ));
				}
			}
		}
		
		return( announce_urls );
	
protected java.lang.StringgetDebugName(ShareResource _share)

		Torrent	torrent = null;
		
		try{
			if ( _share instanceof ShareResourceFile ){
				
				ShareResourceFile share = (ShareResourceFile)_share;
				
				torrent = share.getItem().getTorrent();
				
			}else if ( _share instanceof ShareResourceDir ){
				
				ShareResourceDir share = (ShareResourceDir)_share;
				
				torrent = share.getItem().getTorrent();
			}
		}catch( Throwable e ){			
		}
		
		if ( torrent == null ){
			
			return(	Debug.secretFileName( _share.getName()));
			
		}else{
			
			return( Debug.secretFileName( torrent.getName() ) + "/" + ByteFormatter.encodeString( torrent.getHash()));
		}
	
public ShareResourceDirgetDir(java.io.File file)

		return( (ShareResourceDir)ShareResourceDirImpl.getResource( this, file ));
	
public ShareResourceFilegetFile(java.io.File file)

		return( (ShareResourceFile)ShareResourceFileImpl.getResource( this, file ));
	
protected java.lang.StringgetNewTorrentLocation()

		Random rand = new Random(SystemTime.getCurrentTime());
		
		for (int i=1;i<=MAX_DIRS;i++){
			
			String	cache_dir_str = share_dir + File.separator + TORRENT_SUBSTORE + i;
			
			File	cache_dir = new File(cache_dir_str);
			
			if ( !cache_dir.exists()){
				
				FileUtil.mkdirs(cache_dir);
			}
			
			if ( cache_dir.listFiles().length < MAX_FILES_PER_DIR ){
				
				for (int j=0;j<MAX_FILES_PER_DIR;j++){
					
					long	file = Math.abs(rand.nextLong());
			
					File	file_name = new File(cache_dir_str + File.separator + file + ".torrent");
					
					if ( !file_name.exists()){
						
							// return path relative to cache_dir to save space 
						
						return( TORRENT_SUBSTORE + i + File.separator + file + ".torrent" );
					}
				}
			}
		}
		
		throw( new ShareException( "ShareManager: Failed to allocate cache file"));
	
protected ShareResourceImplgetResource(java.io.File file)

		try{
			return((ShareResourceImpl)shares.get(file.getCanonicalFile().toString()));
			
		}catch( IOException e ){
			
			throw( new ShareException( "getCanonicalFile fails", e ));
		}
	
public ShareResourcegetShare(java.io.File file_or_dir)

		try{
			return( getResource( file_or_dir ));
			
		}catch( ShareException e ){
						
			return( null );
		}
	
protected ShareConfigImplgetShareConfig()

		return( config );
	
public ShareResource[]getShares()

		ShareResource[]	res = new ShareResource[shares.size()];
		
		shares.values().toArray( res );
		
		return( res );
	
public static org.gudy.azureus2.pluginsimpl.local.sharing.ShareManagerImplgetSingleton()

	
	  
	
	
		 
	
		try{
			class_mon.enter();
		
			if ( singleton == null ){
				
				singleton = new ShareManagerImpl();
			}
			
			return( singleton );
			
		}finally{
			
			class_mon.exit();
		}
	
protected java.io.FilegetTorrentFile(ShareItemImpl item)

		return( new File(share_dir+File.separator+item.getTorrentLocation()));
	
public voidinitialise()

		try{
			this_mon.enter();
		
			if ( !initialised ){
			
				try{
					initialising	= true;
					
					initialised		= true;
					
					share_dir = FileUtil.getUserFile( TORRENT_STORE );
					
					FileUtil.mkdirs(share_dir);
									
					config = new ShareConfigImpl();
					
					try{
						config.suspendSaving();
					
						config.loadConfig(this);
				
						checkConsistency();
						
					}finally{
					
						Iterator it = shares.values().iterator();
						
						while(it.hasNext()){
						
							ShareResourceImpl	resource = (ShareResourceImpl)it.next();
							
							if ( resource.getType() == ShareResource.ST_DIR_CONTENTS ){
					
								for (int i=0;i<listeners.size();i++){
									
									try{
										
										((ShareManagerListener)listeners.get(i)).resourceAdded( resource );
										
									}catch( Throwable e ){
										
										Debug.printStackTrace( e );
									}
								}
							}
						}
						
						config.resumeSaving();
					}
					
					readAZConfig();
					
				}finally{
					
					initialising	= false;
				}
			}
		}finally{
			
			this_mon.exit();
		}
	
public booleanisInitialising()

		return( initialising );
	
public voidparameterChanged(java.lang.String name)

		readAZConfigSupport();
	
protected voidreadAZConfig()

		COConfigurationManager.addParameterListener( "Sharing Rescan Enable", this );	
		
		readAZConfigSupport();
	
protected voidreadAZConfigSupport()

		try{
			this_mon.enter();
		
			boolean	scan_enabled	= COConfigurationManager.getBooleanParameter( "Sharing Rescan Enable" );
						
			if ( !scan_enabled ){
			
				current_scanner	= null;
				
			}else if ( current_scanner == null ){
				
				current_scanner = new shareScanner();
			}
			
		}finally{
			
			this_mon.exit();
		}
	
protected voidreadTorrent(ShareItemImpl item)

		try{
			TOTorrent torrent = TOTorrentFactory.deserialiseFromBEncodedFile( getTorrentFile(item ));
			
			item.setTorrent(new TorrentImpl(torrent));
			
		}catch( TOTorrentException e ){
			
			throw( new ShareException( "ShareManager: Torrent read fails", e ));
		}
	
public voidremoveListener(ShareManagerListener l)

		listeners.remove(l);
	
public voidreportCurrentTask(java.lang.String task_description)

		for (int i=0;i<listeners.size();i++){
			
			try{
				
				((ShareManagerListener)listeners.get(i)).reportCurrentTask( task_description );
				
			}catch( Throwable e ){
				
				Debug.printStackTrace( e );
			}
		}			
	
protected voidreportError(java.lang.Throwable e)

		String	message = e.getMessage();
		
		if ( message != null ){
			
			reportCurrentTask( Debug.getNestedExceptionMessage(e));
			
		}else{
			
			reportCurrentTask( e.toString());
		}
	
public voidreportProgress(int percent_complete)

		for (int i=0;i<listeners.size();i++){
			
			try{
				
				((ShareManagerListener)listeners.get(i)).reportProgress( percent_complete );
				
			}catch( Throwable e ){
				
				Debug.printStackTrace( e );
			}
		}		
	
protected voidscanShares()

		if (Logger.isEnabled())
			Logger.log(new LogEvent(LOGID,
					"ShareManager: scanning resources for changes"));

		checkConsistency();
	
protected voidsetTorrentCreator(TOTorrentCreator _to_creator)

		to_creator	= _to_creator;
	
protected booleantorrentExists(ShareItemImpl item)

		
		return( getTorrentFile(item).exists());
	
protected voidwriteTorrent(ShareItemImpl item)

		try{
			item.getTorrent().writeToFile( getTorrentFile(item ));
			
		}catch( TorrentException e ){
			
			throw( new ShareException( "ShareManager: Torrent write fails", e ));
		}