我正在尝试运行spark(2.2)作业,以便使用GRPC(1.1.2)客户端调用从服务器获取一些数据。当我通过spark运行此代码时出现此错误。为小集合运行相同的工作可以正常工作。根据我的研究,我理解ABORTED消息是由于一些并发问题,所以我猜测是因为客户端无法创建超过一定数量的存根,但我不知道如何继续。此外,我知道GRPC服务器可以很好地处理大量请求,而且我远远低于它可以处理的请求数。有任何想法吗?
按要求添加更多信息: 我的客户端CatalogGrpcClient具有处理通道和请求的这些方法:
private List<ManagedChannel> getChannels() {
return IntStream.range(0, numChannels).mapToObj(x ->
ManagedChannelBuilder.forAddress(channelHost, channelPort).usePlaintext(true).build()
).collect(Collectors.toList());
}
private ManagedChannel getChannel() {
return channels.get(ThreadLocalRandom.current().nextInt(channels.size()));
}
private ListingRequest populateRequest(ListingRequest.Builder req, String requestId) {
return req.setClientSendTs(System.currentTimeMillis())
.setRequestId(StringUtils.defaultIfBlank(req.getRequestId(), requestId))
.setSchemaVersion(StringUtils.defaultIfBlank(req.getSchemaVersion(), schema))
.build();
}
private List<ListingResponse> getGrpcListingWithRetry(ListingRequest.Builder request,
String requestIdStr,
int retryLimit,
int sleepBetweenRetry) {
int retryCount = 0;
while (retryCount < retryLimit) {
try {
return StreamSupport.stream(Spliterators.spliteratorUnknownSize(CatalogServiceGrpc.newBlockingStub(getChannel()).getListings(populateRequest(request, requestIdStr)), Spliterator.ORDERED), false).collect(Collectors.toList());
} catch (Exception e) {
System.out.println("Exception " + e.getCause().getMessage());
retryCount = retryCount + 1;
try {
Thread.sleep(sleepBetweenRetry);
} catch (InterruptedException e1) {
e1.printStackTrace();
}
}
}
throw new StatusRuntimeException(Status.ABORTED);
}
我在方法提取中使用getCatalogListingData方法,该方法提取用于映射到spark作业中的case类
def extract(itemIds: List[Long], validAspects: Broadcast[Array[String]]): List[ItemDetailModel] = {
var itemsDetails = List[ItemDetailModel]()
val client = new CatalogGrpcClient()
implicit val formats = DefaultFormats
val listings = client.getCatalogListingData(itemIds.map(x => x.asInstanceOf[java.lang.Long]).asJava).asScala
...
...
itemsDetails
}
这是调用extract的spark代码。 itemsMissingDetails是一个带有“item”列的数据框,该列是唯一的item id列表。 zipWithIndex和以下映射是这样的,我将每个请求中的50个项ID传递给GRPC svc。
itemsMissingDetails
.rdd
.zipWithIndex
.map(x => (x._2 / 50, List(x._1.getLong(0))))
.reduceByKey(_ ++ _)
.flatMap(items => extract(items._2, validAspects))
.toDF
.write
.format("csv")
.option("header",true)
.option("sep", "\t")
.option("escapeQuotes", false)
.save(path)
在很长一段时间(约30分钟到1小时)之后,我的客户实际上抛出了ABORTED错误。当我开始这项工作时,它从GRPC svc获得我需要的信息,每个工人都有几千件物品。在此之后,工作挂起(在每个工人上)并且在经过漫长的等待(约30分钟到1小时)之后,它会因上述异常而失败或继续进行。我无法一直得到StatusRuntimeException。