Mule文件入站流:控制线程数

Mule文件入站流:控制线程数,mule,Mule,我想控制入站文件和消息处理器中的线程数。假设我的输入目录中有5个文件,那么我应该能够一次处理2个文件。一旦这些文件被处理(文件内容由消息处理器处理),那么它只应该拾取其他文件。我曾尝试在流级别使用synchronus处理策略,但它只处理一个文件,我需要多个线程,但每个线程将处理从接收文件到发送响应的消息。我尝试了大卫建议的方法,但也不起作用。一次只拾取一个文件 <flow name="fileInboundTestFlow2" doc:name="fileInboundTestFlow2"

我想控制入站文件和消息处理器中的线程数。假设我的输入目录中有5个文件,那么我应该能够一次处理2个文件。一旦这些文件被处理(文件内容由消息处理器处理),那么它只应该拾取其他文件。我曾尝试在流级别使用synchronus处理策略,但它只处理一个文件,我需要多个线程,但每个线程将处理从接收文件到发送响应的消息。我尝试了大卫建议的方法,但也不起作用。一次只拾取一个文件

<flow name="fileInboundTestFlow2" doc:name="fileInboundTestFlow2" processingStrategy="synchronous">
    <poll frequency="1000">
        <component class="FilePollerComponent" doc:name="File Poller"></component>
    </poll>
    <collection-splitter />
    <request-reply >
            <vm:outbound-endpoint path="out"/>
            <vm:inbound-endpoint path="response">
                               <collection-aggregator/>
            </vm:inbound-endpoint>                      
    </request-reply>
    <file:outbound-endpoint path="E:/fileTest/processed" />
</flow>

public class FilePollerComponent implements Callable{

private String pollDir="E://fileTest" ;

private int numberOfFiles = 3;

public String getPollDir()
{
    return pollDir;
}

public void setPollDir(String pollDir)
{
    this.pollDir = pollDir;
}



public int getNumberOfFiles()
{
    return numberOfFiles;
}

public void setNumberOfFiles(int numberOfFiles)
{
    this.numberOfFiles = numberOfFiles;
}

@Override
public Object onCall(MuleEventContext eventContext) throws Exception
{
    File f = new File(pollDir);
    List<File> filesToReturn = new ArrayList<File>(numberOfFiles);
    if(f.isDirectory())
    {
        File[] files = f.listFiles();
        int i = 0;
        for(File file : files)
        {
            if(file.isFile())
                filesToReturn.add(file);
            if(i==numberOfFiles)
                break ;
            i++;
        }
    }
    else
    {
        throw new Exception("Invalid Directory");
    }
    return filesToReturn;
}}

公共类FilePollerComponent实现可调用{
私有字符串pollDir=“E://fileTest”;
私有int numberOfFiles=3;
公共字符串getPollDir()
{
返回pollDir;
}
公共void setPollDir(字符串pollDir)
{
this.pollDir=pollDir;
}
public int getNumberOfFiles()
{
返回文件数量;
}
public void setNumberOfFiles(int numberOfFiles)
{
this.numberOfFiles=numberOfFiles;
}
@凌驾
公共对象onCall(MuleEventContext eventContext)引发异常
{
文件f=新文件(pollDir);
List filesToReturn=new ArrayList(numberOfFiles);
if(f.isDirectory())
{
File[]files=f.listFiles();
int i=0;
用于(文件:文件)
{
if(file.isFile())
添加(文件);
if(i==numberOfFiles)
打破
i++;
}
}
其他的
{
抛出新异常(“无效目录”);
}
返回文件返回;
}}

文件入站端点是一个轮询器,因此它使用一个线程。如果您使流同步,那么您就是在承载这个单一线程,因此一次只处理一个文件

您需要创建一个只允许2个线程的流处理策略。使用以下允许500个线程的示例:

编辑:上述提案不符合此要求:

若我配置了3个线程,那个么将从输入目录中选取三个文件,并且在处理这些文件之前,不应选取其他文件

事实上,上述建议将始终并行处理3个文件,而不是以3个文件为一组进行处理

所以我提出了另一种方法:

  • 将流处理策略配置为同步
  • 使用
    poll
    元素作为源
  • 在其中放置一个自定义组件,从一个可配置目录中选择3个不同的文件。不需要锁定任何东西,因为流的同步策略阻止了重新进入。返回
    java.io.File
    s的
    java.util.List
  • 在其后面添加一个
    集合拆分器
  • 在入站端点中添加一个带有聚合器的
    请求-应答
    ,以实现fork-join模式()。文件处理将在另一个流中进行,而轮询流将阻塞,直到处理完所有3个文件

我已经试过了,但它是无限循环的。它不断获取文件的锁。我想要的是,单线程应该接收、处理和发送消息。所以,若我配置了3个线程,那个么将从输入目录中选取三个文件,并且在处理这些文件之前,不应选取其他文件。请帮助无限循环听起来像个bug。如果我使用同步流,我已经通过answer。即使文件列表中有三个文件,它仍会一次拾取一个文件。您在
vm:inbound endpoint
中错过了一个聚合器来阻止流的执行,直到处理完这三个文件。尽管如此,它仍只拾取一个文件,但它没有按照需要拾取三个文件。