james-server-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From pgoldst...@apache.org
Subject cvs commit: jakarta-james/src/java/org/apache/james/mailrepository JDBCMailRepository.java
Date Fri, 04 Oct 2002 08:17:50 GMT
pgoldstein    2002/10/04 01:17:50

  Modified:    src/java/org/apache/james/util/mordred JdbcDataSource.java
               src/java/org/apache/james/nntpserver NNTPHandler.java
               src/java/org/apache/james/nntpserver/repository
                        ArticleIDRepository.java NNTPArticleImpl.java
                        NNTPGroup.java NNTPGroupImpl.java
                        NNTPRepositoryImpl.java NNTPSpooler.java
               src/java/org/apache/james/userrepository
                        AbstractJdbcUsersRepository.java
               src/java/org/apache/james/mailrepository
                        JDBCMailRepository.java
  Removed:     src/java/org/apache/james/nntpserver LISTGroup.java
               src/java/org/apache/james/nntpserver/repository
                        NNTPUtil.java
  Log:
  Rearranged object encapsulation for several classes in the NNTP server code
  Fixed a critical threading issue (race condition on creating new articles)
  Reduced group object creation as part of the fix for the threading issue.
  Moved file URL lookup code into a single location.
  Removed extraneous classes to reduce conceptual weight of the NNTP code.
  
  Revision  Changes    Path
  1.17      +2 -6      jakarta-james/src/java/org/apache/james/util/mordred/JdbcDataSource.java
  
  Index: JdbcDataSource.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/util/mordred/JdbcDataSource.java,v
  retrieving revision 1.16
  retrieving revision 1.17
  diff -u -r1.16 -r1.17
  --- JdbcDataSource.java	27 Sep 2002 07:48:40 -0000	1.16
  +++ JdbcDataSource.java	4 Oct 2002 08:17:49 -0000	1.17
  @@ -209,11 +209,7 @@
       }
   
       /**
  -     * Configure and set up DB connection.  Here we set the connection information needed
to create
  -     * the Connection objects.
  -     *
  -     * @param configuration The Configuration object needed to describe the connection.
  -     * @throws ConfigurationException
  +     * @see org.apache.avalon.framework.configuration.Configurable#configure(Configuration)
        */
       public void configure(final Configuration configuration)
                      throws ConfigurationException {
  
  
  
  1.18      +35 -27    jakarta-james/src/java/org/apache/james/nntpserver/NNTPHandler.java
  
  Index: NNTPHandler.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/NNTPHandler.java,v
  retrieving revision 1.17
  retrieving revision 1.18
  diff -u -r1.17 -r1.18
  --- NNTPHandler.java	2 Oct 2002 09:53:38 -0000	1.17
  +++ NNTPHandler.java	4 Oct 2002 08:17:49 -0000	1.18
  @@ -487,7 +487,7 @@
   
           // see section 9.4.1
           String wildmat = "*";
  -        LISTGroup output = null;
  +        boolean isListNewsgroups = false;
   
           String extension = argument;
           if (argument != null) {
  @@ -499,36 +499,44 @@
               extension = extension.toUpperCase(Locale.US);
           }
   
  -        if ((extension == null) || (extension.equals("ACTIVE"))) {
  -            output = LISTGroup.Factory.ACTIVE(writer);
  -        } else if (extension.equals("NEWSGROUPS") ) {
  -            output = LISTGroup.Factory.NEWSGROUPS(writer);
  -        } else if (extension.equals("EXTENSIONS") ) {
  -            doLISTEXTENSIONS();
  -            return;
  -        } else if (extension.equals("OVERVIEW.FMT") ) {
  -            doLISTOVERVIEWFMT();
  -            return;
  -        } else if (extension.equals("ACTIVE.TIMES") ) {
  -            // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  -            writer.println("503 program error, function not performed");
  -            return;
  -        } else if (extension.equals("DISTRIBUTIONS") ) {
  -            // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  -            writer.println("503 program error, function not performed");
  -            return;
  -        } else if (extension.equals("DISTRIB.PATS") ) {
  -            // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  -            writer.println("503 program error, function not performed");
  -            return;
  -        } else {
  -            writer.println("501 Syntax error");
  -            return;
  +        if (extension != null) {
  +            if (extension.equals("ACTIVE")) {
  +                isListNewsgroups = false;
  +            } else if (extension.equals("NEWSGROUPS") ) {
  +                isListNewsgroups = true;
  +            } else if (extension.equals("EXTENSIONS") ) {
  +                doLISTEXTENSIONS();
  +                return;
  +            } else if (extension.equals("OVERVIEW.FMT") ) {
  +                doLISTOVERVIEWFMT();
  +                return;
  +            } else if (extension.equals("ACTIVE.TIMES") ) {
  +                // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  +                writer.println("503 program error, function not performed");
  +                return;
  +            } else if (extension.equals("DISTRIBUTIONS") ) {
  +                // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  +                writer.println("503 program error, function not performed");
  +                return;
  +            } else if (extension.equals("DISTRIB.PATS") ) {
  +                // not supported - 9.4.2.1, 9.4.3.1, 9.4.4.1
  +                writer.println("503 program error, function not performed");
  +                return;
  +            } else {
  +                writer.println("501 Syntax error");
  +                return;
  +            }
           }
  +
           Iterator iter = repo.getMatchedGroups(wildmat);
           writer.println("215 list of newsgroups follows");
           while ( iter.hasNext() ) {
  -            output.show((NNTPGroup)iter.next());
  +            NNTPGroup theGroup = (NNTPGroup)iter.next();
  +            if (isListNewsgroups) {
  +                writer.println(theGroup.getListNewsgroupsFormat());
  +            } else {
  +                writer.println(theGroup.getListFormat());
  +            }
           }
           writer.println(".");
       }
  
  
  
  1.9       +0 -9      jakarta-james/src/java/org/apache/james/nntpserver/repository/ArticleIDRepository.java
  
  Index: ArticleIDRepository.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/ArticleIDRepository.java,v
  retrieving revision 1.8
  retrieving revision 1.9
  diff -u -r1.8 -r1.9
  --- ArticleIDRepository.java	2 Oct 2002 09:53:38 -0000	1.8
  +++ ArticleIDRepository.java	4 Oct 2002 08:17:49 -0000	1.9
  @@ -55,15 +55,6 @@
       }
   
       /**
  -     * Returns the root of the repository.
  -     *
  -     * @return the root of the repository
  -     */
  -    public File getPath() {
  -        return root;
  -    }
  -
  -    /**
        * Generate a new article ID for use in the repository.
        */
       String generateArticleID() {
  
  
  
  1.8       +9 -2      jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPArticleImpl.java
  
  Index: NNTPArticleImpl.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPArticleImpl.java,v
  retrieving revision 1.7
  retrieving revision 1.8
  diff -u -r1.7 -r1.8
  --- NNTPArticleImpl.java	2 Oct 2002 09:53:38 -0000	1.7
  +++ NNTPArticleImpl.java	4 Oct 2002 08:17:49 -0000	1.8
  @@ -25,19 +25,26 @@
       private final File articleFile;
   
       /**
  +     * The newsgroup containing this article.
  +     */
  +    private final NNTPGroup group;
  +
  +    /**
        * The sole constructor for this class.
        *
  +     * @param group the news group containing this article
        * @param f the file that stores the article data
        */
  -    NNTPArticleImpl(File f) {
  +    NNTPArticleImpl(NNTPGroup group, File f) {
           articleFile = f;
  +        this.group = group;
       }
   
       /**
        * @see org.apache.james.nntpsever.repository.NNTPArticle#getGroup()
        */
       public NNTPGroup getGroup() {
  -        return new NNTPGroupImpl(articleFile.getParentFile());
  +        return group;
       }
   
       /**
  
  
  
  1.4       +25 -3     jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPGroup.java
  
  Index: NNTPGroup.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPGroup.java,v
  retrieving revision 1.3
  retrieving revision 1.4
  diff -u -r1.3 -r1.4
  --- NNTPGroup.java	2 Oct 2002 09:53:38 -0000	1.3
  +++ NNTPGroup.java	4 Oct 2002 08:17:49 -0000	1.4
  @@ -7,6 +7,8 @@
    */
   package org.apache.james.nntpserver.repository;
   
  +import java.io.InputStream;
  +import java.io.IOException;
   import java.util.Date;
   import java.util.Iterator;
   
  @@ -109,8 +111,28 @@
       Iterator getArticles();
   
       /**
  -     * TODO: I don't understand the purpose of this method.  It seems to 
  -     *       be an implementation hack.  
  +     * Retrieves the group information in a format consistent with
  +     * a LIST or LIST ACTIVE return line
  +     *
  +     * @return the properly formatted string
  +     */
  +    String getListFormat();
  +
  +    /**
  +     * Retrieves the group information in a format consistent with
  +     * a LIST NEWSGROUPS return line
  +     *
  +     * @return the properly formatted string
  +     */
  +    String getListNewsgroupsFormat();
  +
  +    /**
  +     * Adds an article to the group based on the data in the
  +     * stream.
  +     *
  +     * @param newsStream the InputStream containing the article data
  +     *
  +     * @return the newly created article
        */
  -    Object getPath();
  +    NNTPArticle addArticle(InputStream newsStream) throws IOException;
   }
  
  
  
  1.7       +67 -7     jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPGroupImpl.java
  
  Index: NNTPGroupImpl.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPGroupImpl.java,v
  retrieving revision 1.6
  retrieving revision 1.7
  diff -u -r1.6 -r1.7
  --- NNTPGroupImpl.java	2 Oct 2002 09:53:38 -0000	1.6
  +++ NNTPGroupImpl.java	4 Oct 2002 08:17:49 -0000	1.7
  @@ -10,9 +10,14 @@
   import org.apache.avalon.excalibur.io.AndFileFilter;
   import org.apache.avalon.excalibur.io.ExtensionFileFilter;
   import org.apache.avalon.excalibur.io.InvertedFileFilter;
  +import org.apache.avalon.excalibur.io.IOUtil;
  +import org.apache.avalon.framework.logger.AbstractLogEnabled;
   import org.apache.james.nntpserver.DateSinceFileFilter;
   
   import java.io.File;
  +import java.io.FileOutputStream;
  +import java.io.InputStream;
  +import java.io.IOException;
   import java.util.ArrayList;
   import java.util.Date;
   import java.util.Iterator;
  @@ -24,7 +29,7 @@
    *
    * @author Harmeet Bedi <harmeet@kodemuse.com>
    */
  -class NNTPGroupImpl implements NNTPGroup {
  +class NNTPGroupImpl extends AbstractLogEnabled implements NNTPGroup {
   
       /**
        * The directory to which this group maps.
  @@ -168,7 +173,7 @@
        */
       public NNTPArticle getArticle(int number) {
           File f = new File(root,number + "");
  -        return f.exists() ? new NNTPArticleImpl(f) : null;
  +        return f.exists() ? new NNTPArticleImpl(this, f) : null;
       }
   
       /**
  @@ -180,7 +185,7 @@
                new InvertedFileFilter(new ExtensionFileFilter(".id"))));
           List list = new ArrayList();
           for ( int i = 0 ; i < f.length ; i++ )
  -            list.add(new NNTPArticleImpl(f[i]));
  +            list.add(new NNTPArticleImpl(this, f[i]));
           return list.iterator();
       }
   
  @@ -191,15 +196,70 @@
           File[] f = root.listFiles();
           List list = new ArrayList();
           for ( int i = 0 ; i < f.length ; i++ )
  -            list.add(new NNTPArticleImpl(f[i]));
  +            list.add(new NNTPArticleImpl(this, f[i]));
           return list.iterator();
       }
   
       /**
  -     * @see org.apache.james.nntpserver.NNTPGroup#getPath()
  +     * @see org.apache.james.nntpserver.repository.NNTPGroup#getListFormat()
        */
  -    public Object getPath() {
  -        return root;
  +    public String getListFormat() {
  +        StringBuffer showBuffer =
  +            new StringBuffer(128)
  +                .append(getName())
  +                .append(" ")
  +                .append(getFirstArticleNumber())
  +                .append(" ")
  +                .append(getLastArticleNumber())
  +                .append(" ")
  +                .append((isPostAllowed() ? "y":"n"));
  +        return showBuffer.toString();
  +    }
  +
  +    /**
  +     * @see org.apache.james.nntpserver.repository.NNTPGroup#getListNewsgroupsFormat()
  +     */
  +    public String getListNewsgroupsFormat() {
  +        StringBuffer showBuffer =
  +            new StringBuffer(128)
  +                .append(getName())
  +                .append(" ")
  +                .append(getDescription());
  +         return showBuffer.toString();
  +    }
  +
  +    /**
  +     * @see org.apache.james.nntpserver.repository.NNTPGroup#addArticle(InputStream)
  +     */
  +    public NNTPArticle addArticle(InputStream newsStream)
  +            throws IOException {
  +        File articleFile = null;
  +        synchronized (this) {
  +            int artNum = getLastArticleNumber();
  +            articleFile = new File(root,(artNum + 1)+"");
  +            articleFile.createNewFile();
  +            lastArticle++;
  +            numOfArticles++;
  +        }
  +        if (getLogger().isDebugEnabled()) {
  +            getLogger().debug("Copying message to: "+articleFile.getAbsolutePath());
  +        }
  +        FileOutputStream fout = null;
  +        try {
  +            fout = new FileOutputStream(articleFile);
  +            IOUtil.copy(newsStream,fout);
  +            fout.flush();
  +        } finally {
  +            try {
  +                if (fout != null) {
  +                    fout.close();
  +                }
  +            } catch (IOException ioe) {
  +                // Ignore this exception so we don't
  +                // trash any "real" exceptions
  +            }
  +        }
  +        return new NNTPArticleImpl(this, articleFile);
       }
   
   //     public NNTPArticle getArticleFromID(String id) {
  
  
  
  1.10      +139 -38   jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPRepositoryImpl.java
  
  Index: NNTPRepositoryImpl.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPRepositoryImpl.java,v
  retrieving revision 1.9
  retrieving revision 1.10
  diff -u -r1.9 -r1.10
  --- NNTPRepositoryImpl.java	2 Oct 2002 09:53:38 -0000	1.9
  +++ NNTPRepositoryImpl.java	4 Oct 2002 08:17:49 -0000	1.10
  @@ -17,6 +17,8 @@
   import org.apache.avalon.framework.context.ContextException;
   import org.apache.avalon.framework.context.Contextualizable;
   import org.apache.avalon.framework.logger.AbstractLogEnabled;
  +import org.apache.avalon.framework.logger.LogEnabled;
  +import org.apache.james.context.AvalonContextUtilities;
   import org.apache.james.nntpserver.DateSinceFileFilter;
   import org.apache.james.nntpserver.NNTPException;
   import org.apache.oro.io.GlobFilenameFilter;
  @@ -27,6 +29,7 @@
   import java.io.PrintStream;
   import java.util.ArrayList;
   import java.util.Date;
  +import java.util.HashMap;
   import java.util.Iterator;
   import java.util.List;
   
  @@ -44,6 +47,11 @@
       private Context context;
   
       /**
  +     * The configuration employed by this repository
  +     */
  +    private Configuration configuration;
  +
  +    /**
        * Whether the repository is read only
        */
       private boolean readOnly;
  @@ -74,6 +82,33 @@
       private String[] addGroups = null;
   
       /**
  +     * The root path as a String.
  +     */
  +    private String rootPathString = null;
  +
  +    /**
  +     * The temp path as a String.
  +     */
  +    private String tempPathString = null;
  +
  +    /**
  +     * The article ID path as a String.
  +     */
  +    private String articleIdPathString = null;
  +
  +    /**
  +     * The domain suffix used for files in the article ID repository.
  +     */
  +    private String articleIDDomainSuffix = null;
  +
  +    /**
  +     * This is a mapping of group names to NNTP group objects.
  +     *
  +     * TODO: This needs to be addressed so it scales better
  +     */
  +    private HashMap repositoryGroups = new HashMap();
  +
  +    /**
        * @see org.apache.avalon.framework.context.Contextualizable#contextualize(Context)
        */
       public void contextualize(Context context)
  @@ -84,62 +119,70 @@
       /**
        * @see org.apache.avalon.framework.configuration.Configurable#configure(Configuration)
        */
  -    public void configure( Configuration configuration ) throws ConfigurationException
{
  -        //System.out.println(getClass().getName() + ": configure");
  -        //NNTPUtil.show(configuration,System.out);
  +    public void configure( Configuration aConfiguration ) throws ConfigurationException
{
  +        configuration = aConfiguration;
           readOnly = configuration.getChild("readOnly").getValueAsBoolean(false);
  -        rootPath = NNTPUtil.getDirectory(context, configuration, "rootPath");
  -        tempPath = NNTPUtil.getDirectory(context, configuration, "tempPath");
  -        File articleIDPath = NNTPUtil.getDirectory(context, configuration, "articleIDPath");
  -        String articleIDDomainSuffix = configuration.getChild("articleIDDomainSuffix")
  -            .getValue("foo.bar.sho.boo");
  -        articleIDRepo = new ArticleIDRepository(articleIDPath,articleIDDomainSuffix);
  -        spool = (NNTPSpooler)NNTPUtil.createInstance
  -            (context,configuration.getChild("spool"),getLogger(),
  -             "org.apache.james.nntpserver.repository.NNTPSpooler");
  -        spool.setRepository(this);
  -        spool.setArticleIDRepository(articleIDRepo);
  -        if (getLogger().isDebugEnabled()) {
  -            getLogger().debug("repository:readOnly=" + readOnly);
  -            getLogger().debug("repository:rootPath=" + rootPath.getAbsolutePath());
  -            getLogger().debug("repository:tempPath=" + tempPath.getAbsolutePath());
  -        }
  -        configuration = configuration.getChild("newsgroups");
  +        Configuration newsgroupConfiguration = configuration.getChild("newsgroups");
           List addGroupsList = new ArrayList();
           if ( configuration != null ) {
  -            Configuration[] children = configuration.getChildren("newsgroup");
  -            if ( children != null )
  -                for ( int i = 0 ; i < children.length ; i++ )
  +            Configuration[] children = newsgroupConfiguration.getChildren("newsgroup");
  +            if ( children != null ) {
  +                for ( int i = 0 ; i < children.length ; i++ ) {
                       addGroupsList.add(children[i].getValue());
  +                }
  +            }
           }
  +        articleIDDomainSuffix = configuration.getChild("articleIDDomainSuffix")
  +            .getValue("foo.bar.sho.boo");
           addGroups = (String[])addGroupsList.toArray(new String[0]);
  -        getLogger().debug("repository configuration done");
  +        rootPathString = configuration.getChild("rootPath").getValue();
  +        tempPathString = configuration.getChild("tempPath").getValue();
  +        articleIdPathString = configuration.getChild("articleIDPath").getValue();
  +        getLogger().debug("Repository configuration done");
       }
   
       /**
        * @see org.apache.avalon.framework.activity.Initializable#initialize()
        */
       public void initialize() throws Exception {
  -        //System.out.println(getClass().getName() + ": init");
  +
  +        File articleIDPath = null;
  +
  +        try {
  +            rootPath = AvalonContextUtilities.getFile(context, rootPathString);
  +            tempPath = AvalonContextUtilities.getFile(context, tempPathString);
  +            articleIDPath = AvalonContextUtilities.getFile(context, articleIdPathString);
  +        } catch (Exception e) {
  +            getLogger().fatalError(e.getMessage(), e);
  +            throw e;
  +        }
  +
  +        if ( articleIDPath.exists() == false ) {
  +            articleIDPath.mkdirs();
  +        }
  +
  +        articleIDRepo = new ArticleIDRepository(articleIDPath, articleIDDomainSuffix);
  +        spool = (NNTPSpooler)createSpooler();
  +        spool.setRepository(this);
  +        spool.setArticleIDRepository(articleIDRepo);
  +        if (getLogger().isDebugEnabled()) {
  +            getLogger().debug("repository:readOnly=" + readOnly);
  +            getLogger().debug("repository:rootPath=" + rootPath.getAbsolutePath());
  +            getLogger().debug("repository:tempPath=" + tempPath.getAbsolutePath());
  +        }
  +
           if ( rootPath.exists() == false ) {
               rootPath.mkdirs();
           }
           for ( int i = 0 ; i < addGroups.length ; i++ ) {
  -            File groupF = new File(rootPath,addGroups[i]);
  -            if ( groupF.exists() == false ) {
  -                groupF.mkdirs();
  +            File groupFile = new File(rootPath,addGroups[i]);
  +            if ( groupFile.exists() == false ) {
  +                groupFile.mkdirs();
               }
           }
           if ( tempPath.exists() == false ) {
               tempPath.mkdirs();
           }
  -        File articleIDPath = articleIDRepo.getPath();
  -        if ( articleIDPath.exists() == false ) {
  -            articleIDPath.mkdirs();
  -        }
  -        if ( spool instanceof Initializable ) {
  -            ((Initializable)spool).initialize();
  -        }
           getLogger().debug("repository initialization done");
       }
   
  @@ -154,8 +197,17 @@
        * @see org.apache.james.nntpserver.repository.NNTPRepository#getGroup(String)
        */
       public NNTPGroup getGroup(String groupName) {
  -        File f = new File(rootPath,groupName);
  -        return ( f.exists() && f.isDirectory() ) ? new NNTPGroupImpl(f) : null;
  +        File groupFile = new File(rootPath,groupName);
  +        NNTPGroup groupToReturn = null;
  +        synchronized(this) {
  +            groupToReturn = (NNTPGroup)repositoryGroups.get(groupName);
  +            if ((groupToReturn == null) && groupFile.exists() && groupFile.isDirectory()
) {
  +                groupToReturn = new NNTPGroupImpl(groupFile);
  +                ((NNTPGroupImpl)groupToReturn).enableLogging(getLogger());
  +                repositoryGroups.put(groupName, groupToReturn);
  +            }
  +        }
  +        return groupToReturn;
       }
   
       /**
  @@ -219,7 +271,9 @@
       private Iterator getGroups(File[] f) {
           List list = new ArrayList();
           for ( int i = 0 ; i < f.length ; i++ ) {
  -            list.add(new NNTPGroupImpl(f[i]));
  +            if (f[i] != null) {
  +                list.add(getGroup(f[i].getName()));
  +            }
           }
           return list.iterator();
       }
  @@ -273,4 +327,51 @@
                   }
               };
       }
  +
  +    /**
  +     * Creates an instance of the spooler class.
  +     *
  +     * TODO: This method doesn't properly implement the Avalon lifecycle.
  +     */
  +    private NNTPSpooler createSpooler() 
  +            throws ConfigurationException {
  +        String className = "org.apache.james.nntpserver.repository.NNTPSpooler";
  +        Configuration spoolerConfiguration = configuration.getChild("spool");
  +        try {
  +            // Must be a subclass of org.apache.james.nntpserver.repository.NNTPSpooler
  +            className = spoolerConfiguration.getAttribute("class");
  +        } catch(ConfigurationException ce) {
  +            // Use the default class.
  +        }
  +        try {
  +            Object obj = getClass().getClassLoader().loadClass(className).newInstance();
  +            // TODO: Need to support compose
  +            if ( obj instanceof LogEnabled ) {
  +                ((LogEnabled)obj).enableLogging( getLogger() );
  +            }
  +            if (obj instanceof Contextualizable) {
  +                ((Contextualizable)obj).contextualize(context);
  +            }
  +            if ( obj instanceof Configurable ) {
  +                ((Configurable)obj).configure(spoolerConfiguration.getChild("configuration"));
  +            }
  +            if ( obj instanceof Initializable ) {
  +                ((Initializable)obj).initialize();
  +            }
  +            return (NNTPSpooler)obj;
  +        } catch(ClassCastException cce) {
  +            StringBuffer errorBuffer =
  +                new StringBuffer(128)
  +                    .append("Spooler initialization failed because the spooler class ")
  +                    .append(className)
  +                    .append(" was not a subclass of org.apache.james.nntpserver.repository.NNTPSpooler");
  +            String errorString = errorBuffer.toString();
  +            getLogger().error(errorString, cce);
  +            throw new ConfigurationException(errorString, cce);
  +        } catch(Exception ex) {
  +            getLogger().error("Spooler initialization failed",ex);
  +            throw new ConfigurationException("Spooler initialization failed",ex);
  +        }
  +    }
  +
   }
  
  
  
  1.9       +48 -46    jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPSpooler.java
  
  Index: NNTPSpooler.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/nntpserver/repository/NNTPSpooler.java,v
  retrieving revision 1.8
  retrieving revision 1.9
  diff -u -r1.8 -r1.9
  --- NNTPSpooler.java	2 Oct 2002 09:53:38 -0000	1.8
  +++ NNTPSpooler.java	4 Oct 2002 08:17:49 -0000	1.9
  @@ -7,7 +7,6 @@
    */
   package org.apache.james.nntpserver.repository;
   
  -import org.apache.avalon.excalibur.io.IOUtil;
   import org.apache.avalon.framework.activity.Initializable;
   import org.apache.avalon.framework.configuration.Configurable;
   import org.apache.avalon.framework.configuration.Configuration;
  @@ -17,6 +16,7 @@
   import org.apache.avalon.framework.context.Contextualizable;
   import org.apache.avalon.framework.logger.AbstractLogEnabled;
   import org.apache.avalon.framework.logger.LogEnabled;
  +import org.apache.james.context.AvalonContextUtilities;
   import org.apache.james.util.Lock;
   
   import javax.mail.internet.MimeMessage;
  @@ -50,6 +50,16 @@
       private File spoolPath;
   
       /**
  +     * The String form of the spool directory.
  +     */
  +    private String spoolPathString;
  +
  +    /**
  +     * The time the spooler threads sleep between processing
  +     */
  +    private int threadIdleTime = 0;
  +
  +    /**
        * @see org.apache.avalon.framework.context.Contextualizable#contextualize(Context)
        */
       public void contextualize(final Context context) 
  @@ -61,17 +71,36 @@
        * @see org.apache.avalon.framework.configuration.Configurable#configure(Configuration)
        */
       public void configure( Configuration configuration ) throws ConfigurationException
{
  -        spoolPath = NNTPUtil.getDirectory(context, configuration, "spoolPath");
           int threadCount = configuration.getChild("threadCount").getValueAsInteger(1);
  -        int threadIdleTime = configuration.getChild("threadIdleTime").getValueAsInteger(1000);
  -        //String tgName=configuration.getChild("threadGroupName").getValue("NNTPSpooler");
  +        threadIdleTime = configuration.getChild("threadIdleTime").getValueAsInteger(1000);
  +        spoolPathString = configuration.getChild("spoolPath").getValue();
           worker = new SpoolerRunnable[threadCount];
  +    }
  +
  +    /**
  +     * @see org.apache.avalon.framework.activity.Initializable#initialize()
  +     */
  +    public void initialize() throws Exception {
  +        //System.out.println(getClass().getName()+": init");
  +
  +        try {
  +            spoolPath = AvalonContextUtilities.getFile(context, spoolPathString);
  +        } catch (Exception e) {
  +            getLogger().fatalError(e.getMessage(), e);
  +            throw e;
  +        }
  +
           for ( int i = 0 ; i < worker.length ; i++ ) {
               worker[i] = new SpoolerRunnable(threadIdleTime,spoolPath);
               if ( worker[i] instanceof LogEnabled ) {
                   ((LogEnabled)worker[i]).enableLogging(getLogger());
               }
           }
  +
  +        // TODO: Replace this with a standard Avalon thread pool
  +        for ( int i = 0 ; i < worker.length ; i++ ) {
  +            new Thread(worker[i],"NNTPSpool-"+i).start();
  +        }
       }
   
       /**
  @@ -110,17 +139,6 @@
       }
   
       /**
  -     * @see org.apache.avalon.framework.activity.Initializable#initialize()
  -     */
  -    public void initialize() throws Exception {
  -        //System.out.println(getClass().getName()+": init");
  -        // TODO: Replace this with a standard Avalon thread pool
  -        for ( int i = 0 ; i < worker.length ; i++ ) {
  -            new Thread(worker[i],"NNTPSpool-"+i).start();
  -        }
  -    }
  -
  -    /**
        * A static inner class that provides the body for the spool
        * threads.
        */
  @@ -206,34 +224,34 @@
            *
            * @param f the spool file being processed
            */
  -        private void process(File f) throws Exception {
  +        private void process(File spoolFile) throws Exception {
               StringBuffer logBuffer =
                   new StringBuffer(160)
                           .append("process: ")
  -                        .append(f.getAbsolutePath())
  +                        .append(spoolFile.getAbsolutePath())
                           .append(",")
  -                        .append(f.getCanonicalPath());
  +                        .append(spoolFile.getCanonicalPath());
               getLogger().debug(logBuffer.toString());
               final MimeMessage msg;
               String articleID;
               // TODO: Why is this a block?
  -            {   // get the message for copying to destination groups.
  -                FileInputStream fin = new FileInputStream(f);
  +            {   // Get the message for copying to destination groups.
  +                FileInputStream fin = new FileInputStream(spoolFile);
                   msg = new MimeMessage(null,fin);
                   fin.close();
   
                   // ensure no duplicates exist.
                   String[] idheader = msg.getHeader("Message-Id");
  -                articleID = (idheader!=null && idheader.length>0?idheader[0]:null);
  -                if ( articleIDRepo.isExists(articleID) ) {
  +                articleID = ((idheader != null && (idheader.length > 0))? idheader[0]
: null);
  +                if ((articleID != null) && ( articleIDRepo.isExists(articleID)))
{
                       getLogger().debug("Message already exists: "+articleID);
  -                    f.delete();
  +                    spoolFile.delete();
                       return;
                   }
                   if ( articleID == null ) {
                       articleID = articleIDRepo.generateArticleID();
                       msg.setHeader("Message-Id", articleID);
  -                    FileOutputStream fout = new FileOutputStream(f);
  +                    FileOutputStream fout = new FileOutputStream(spoolFile);
                       msg.writeTo(fout);
                       fout.close();
                   }
  @@ -245,34 +263,18 @@
                   getLogger().debug("Copying message to group: "+headers[i]);
                   NNTPGroup group = repo.getGroup(headers[i]);
                   if ( group == null ) {
  -                    getLogger().debug("Group not found: "+headers[i]);
  +                    getLogger().error("Couldn't add article with article ID " + articleID
+ " to group " + headers[i] + " - group not found.");
                       continue;
                   }
  -                int artNum = group.getLastArticleNumber();
   
  -                // TODO: Encapsulate this in the NNTP group.
  -                File root = (File)group.getPath();
  -                File articleFile = null;
  -                // this ensures that different threads do not create articles with
  -                // same number
  -                while( true ) {
  -                    articleFile = new File(root,(artNum+1)+"");
  -                    if (articleFile.createNewFile()) {
  -                        break;
  -                    }
  -                }
  -                getLogger().debug("Copying message to: "+articleFile.getAbsolutePath());
  -                prop.setProperty(group.getName(),articleFile.getName());
  -                FileInputStream fin = new FileInputStream(f);
  -                FileOutputStream fout = new FileOutputStream(articleFile);
  -                IOUtil.copy(fin,fout);
  -                fin.close();
  -                fout.close();
  +                FileInputStream newsStream = new FileInputStream(spoolFile);
  +                NNTPArticle article = group.addArticle(newsStream);
  +                prop.setProperty(group.getName(),article.getArticleNumber() + "");
               }
               articleIDRepo.addArticle(articleID,prop);
  -            boolean delSuccess = f.delete();
  +            boolean delSuccess = spoolFile.delete();
               if ( delSuccess == false ) {
  -                getLogger().error("Could not delete file: "+f.getAbsolutePath());
  +                getLogger().error("Could not delete file: " + spoolFile.getAbsolutePath());
               }
           }
       } // class SpoolerRunnable
  
  
  
  1.13      +10 -26    jakarta-james/src/java/org/apache/james/userrepository/AbstractJdbcUsersRepository.java
  
  Index: AbstractJdbcUsersRepository.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/userrepository/AbstractJdbcUsersRepository.java,v
  retrieving revision 1.12
  retrieving revision 1.13
  diff -u -r1.12 -r1.13
  --- AbstractJdbcUsersRepository.java	2 Oct 2002 06:12:03 -0000	1.12
  +++ AbstractJdbcUsersRepository.java	4 Oct 2002 08:17:49 -0000	1.13
  @@ -21,7 +21,7 @@
   import org.apache.avalon.framework.context.Context;
   import org.apache.avalon.framework.context.ContextException;
   import org.apache.avalon.framework.context.Contextualizable;
  -import org.apache.james.context.AvalonContextConstants;
  +import org.apache.james.context.AvalonContextUtilities;
   import org.apache.james.services.User;
   import org.apache.james.util.JDBCUtil;
   import org.apache.james.util.SqlResources;
  @@ -243,30 +243,15 @@
           try{
               DatabaseMetaData dbMetaData = conn.getMetaData();
   
  -            // Initialise the sql strings.
  -            String fileName = m_sqlFileName.substring("file://".length());
  -            if (!(fileName.startsWith("/"))) {
  -                String baseDirectory = "";
  -                try {
  -                    File applicationHome =
  -                        (File)context.get(AvalonContextConstants.APPLICATION_HOME);
  -                    baseDirectory = applicationHome.toString();
  -                } catch (ContextException ce) {
  -                    getLogger().fatalError("Encountered exception when resolving application
home in Avalon context.", ce);
  -                    throw ce;
  -                } catch (ClassCastException cce) {
  -                    getLogger().fatalError("Application home object stored in Avalon context
was not of type java.io.File.", cce);
  -                    throw cce;
  -                }
  -                StringBuffer fileNameBuffer =
  -                    new StringBuffer(128)
  -                            .append(baseDirectory)
  -                            .append(File.separator)
  -                            .append(fileName);
  -                fileName = fileNameBuffer.toString();
  +            File sqlFile = null;
  +
  +            try {
  +                sqlFile = AvalonContextUtilities.getFile(context, m_sqlFileName);
  +            } catch (Exception e) {
  +                getLogger().fatalError(e.getMessage(), e);
  +                throw e;
               }
  -            File sqlFile = (new File(fileName)).getCanonicalFile();
  -            
  +
               if (getLogger().isDebugEnabled()) {
                   logBuffer =
                       new StringBuffer(256)
  @@ -337,8 +322,7 @@
                               .append(tableName)
                               .append("\'.");
                   getLogger().info(logBuffer.toString());
  -            }
  -            else {
  +            } else {
                   if (getLogger().isDebugEnabled()) {
                       getLogger().debug("Using table: " + tableName);
                   }
  
  
  
  1.29      +8 -22     jakarta-james/src/java/org/apache/james/mailrepository/JDBCMailRepository.java
  
  Index: JDBCMailRepository.java
  ===================================================================
  RCS file: /home/cvs/jakarta-james/src/java/org/apache/james/mailrepository/JDBCMailRepository.java,v
  retrieving revision 1.28
  retrieving revision 1.29
  diff -u -r1.28 -r1.29
  --- JDBCMailRepository.java	2 Oct 2002 06:12:02 -0000	1.28
  +++ JDBCMailRepository.java	4 Oct 2002 08:17:49 -0000	1.29
  @@ -24,7 +24,7 @@
   import org.apache.avalon.framework.context.ContextException;
   import org.apache.avalon.framework.context.Contextualizable;
   import org.apache.avalon.framework.logger.AbstractLogEnabled;
  -import org.apache.james.context.AvalonContextConstants;
  +import org.apache.james.context.AvalonContextUtilities;
   import org.apache.james.core.MailImpl;
   import org.apache.james.core.MimeMessageWrapper;
   import org.apache.james.services.MailRepository;
  @@ -309,28 +309,14 @@
   
           try {
               // Initialise the sql strings.
  -            String fileName = sqlFileName.substring("file://".length());
  -            if (!(fileName.startsWith("/"))) {
  -                String baseDirectory = "";
  -                try {
  -                    File applicationHome =
  -                        (File)context.get(AvalonContextConstants.APPLICATION_HOME);
  -                    baseDirectory = applicationHome.toString();
  -                } catch (ContextException ce) {
  -                    getLogger().fatalError("Encountered exception when resolving application
home in Avalon context.", ce);
  -                    throw ce;
  -                } catch (ClassCastException cce) {
  -                    getLogger().fatalError("Application home object stored in Avalon context
was not of type java.io.File.", cce);
  -                    throw cce;
  -                }
  -                StringBuffer fileNameBuffer =
  -                    new StringBuffer(128)
  -                            .append(baseDirectory)
  -                            .append(File.separator)
  -                            .append(fileName);
  -                fileName = fileNameBuffer.toString();
  +
  +            File sqlFile = null;
  +            try {
  +                sqlFile = AvalonContextUtilities.getFile(context, sqlFileName);
  +            } catch (Exception e) {
  +                getLogger().fatalError(e.getMessage(), e);
  +                throw e;
               }
  -            File sqlFile = (new File(fileName)).getCanonicalFile();
   
               String resourceName = "org.apache.james.mailrepository.JDBCMailRepository";
   
  
  
  

--
To unsubscribe, e-mail:   <mailto:james-dev-unsubscribe@jakarta.apache.org>
For additional commands, e-mail: <mailto:james-dev-help@jakarta.apache.org>


Mime
View raw message