Search in sources :

Example 1 with StringTool

use of io.datarouter.util.string.StringTool in project datarouter by hotpads.

the class LoadTestGetHandler method get.

@Handler(defaultHandler = true)
private Mav get(@Param(P_num) OptionalString num, @Param(P_max) OptionalString max, @Param(P_numThreads) OptionalString numThreads, @Param(P_batchSize) OptionalString batchSize, @Param(P_logPeriod) OptionalString logPeriod, @Param(P_submitAction) OptionalString submitAction) {
    var form = new HtmlForm().withMethod("post");
    form.addTextField().withDisplay("Num").withName(P_num).withPlaceholder("100,000").withValue(num.orElse(null));
    form.addTextField().withDisplay("Max").withName(P_max).withPlaceholder("10").withValue(max.orElse(null));
    form.addTextField().withDisplay("Num Threads").withName(P_numThreads).withPlaceholder("10").withValue(numThreads.orElse(null));
    form.addTextField().withDisplay("Batch Size").withName(P_batchSize).withPlaceholder("100").withValue(batchSize.orElse(null));
    form.addTextField().withDisplay("Log Period").withName(P_logPeriod).withPlaceholder("1,0000").withValue(logPeriod.orElse(null));
    form.addButton().withDisplay("Run Get").withValue("anything");
    if (submitAction.isEmpty() || form.hasErrors()) {
        return pageFactory.startBuilder(request).withTitle("Load Test - Get").withContent(Html.makeContent(form)).buildMav();
    }
    PhaseTimer timer = new PhaseTimer("get");
    // params
    int pNum = num.map(StringTool::nullIfEmpty).map(number -> number.replaceAll(",", "")).map(Integer::valueOf).orElse(DEFAULT_NUM);
    int pMax = max.map(StringTool::nullIfEmpty).map(number -> number.replaceAll(",", "")).map(Integer::valueOf).orElse(pNum);
    int pNumThreads = numThreads.map(StringTool::nullIfEmpty).map(number -> number.replaceAll(",", "")).map(Integer::valueOf).orElse(DEFAULT_NUM_THREADS);
    int pBatchSize = batchSize.map(StringTool::nullIfEmpty).map(number -> number.replaceAll(",", "")).map(Integer::valueOf).orElse(DEFAULT_BATCH_SIZE);
    int pLogPeriod = logPeriod.map(StringTool::nullIfEmpty).map(number -> number.replaceAll(",", "")).map(Integer::valueOf).orElse(DEFAULT_LOG_PERIOD);
    // tracking
    AtomicInteger rowCounter = new AtomicInteger(0);
    AtomicLong lastBatchFinished = new AtomicLong(System.nanoTime());
    // execute
    int numBatches = LoadTestTool.numBatches(pNum, pBatchSize);
    ExecutorService executor = Executors.newFixedThreadPool(pNumThreads);
    Scanner.of(IntStream.range(0, numBatches).mapToObj(Integer::valueOf)).map(batchId -> LoadTestTool.makeRandomIdBatch(pNum, pMax, pBatchSize, batchId)).map(ids -> new GetBatchCallable(dao.getReaderNode(), ids, pLogPeriod, rowCounter, lastBatchFinished)).parallel(new ParallelScannerContext(executor, pNumThreads, true)).forEach(CallableTool::callUnchecked);
    ExecutorServiceTool.shutdown(executor, Duration.ofSeconds(5));
    timer.add("got " + rowCounter.get());
    var message = div(h2("Load Test Get Results"), div(h3("Results"), dl(dt("Total Time"), dd(timer.getElapsedString()), dt("Rows per second"), dd(timer.getItemsPerSecond(rowCounter.get()) + ""))), div(h3("Params"), dl(dt("Num"), dd(pNum + ""), dt("Max"), dd(pMax + ""), dt("Num Threads"), dd(pNumThreads + ""), dt("Batch Size"), dd(pBatchSize + ""), dt("Log Period"), dd(pLogPeriod + "")))).withClass("container");
    logger.warn("total={}, rps={}, num={}, max={}, numThreads={} batchSize={}, logPeriod={}", timer.getElapsedString(), timer.getItemsPerSecond(rowCounter.get()), pNum, pMax, pNumThreads, pBatchSize, pLogPeriod);
    return pageFactory.message(request, message);
}
Also used : IntStream(java.util.stream.IntStream) Scanner(io.datarouter.scanner.Scanner) ParallelScannerContext(io.datarouter.scanner.ParallelScannerContext) TagCreator.dd(j2html.TagCreator.dd) LoggerFactory(org.slf4j.LoggerFactory) TagCreator.h3(j2html.TagCreator.h3) Callable(java.util.concurrent.Callable) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TagCreator.h2(j2html.TagCreator.h2) TagCreator.dl(j2html.TagCreator.dl) Inject(javax.inject.Inject) NumberFormatter(io.datarouter.util.number.NumberFormatter) ExecutorServiceTool(io.datarouter.util.concurrent.ExecutorServiceTool) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) TagCreator.br(j2html.TagCreator.br) TagCreator.dt(j2html.TagCreator.dt) Duration(java.time.Duration) Param(io.datarouter.web.handler.types.Param) Bootstrap4FormHtml(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml) ExecutorService(java.util.concurrent.ExecutorService) PhaseTimer(io.datarouter.util.timer.PhaseTimer) Logger(org.slf4j.Logger) Mav(io.datarouter.web.handler.mav.Mav) RandomValue(io.datarouter.loadtest.storage.RandomValue) StringTool(io.datarouter.util.string.StringTool) Executors(java.util.concurrent.Executors) ContainerTag(j2html.tags.ContainerTag) AtomicLong(java.util.concurrent.atomic.AtomicLong) List(java.util.List) LoadTestTool(io.datarouter.loadtest.util.LoadTestTool) HtmlForm(io.datarouter.web.html.form.HtmlForm) BaseHandler(io.datarouter.web.handler.BaseHandler) LoadTestGetDao(io.datarouter.loadtest.service.LoadTestGetDao) CallableTool(io.datarouter.util.concurrent.CallableTool) Bootstrap4PageFactory(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory) RandomValueKey(io.datarouter.loadtest.storage.RandomValueKey) TagCreator.div(j2html.TagCreator.div) MapStorageReader(io.datarouter.storage.node.op.raw.read.MapStorageReader) AtomicLong(java.util.concurrent.atomic.AtomicLong) PhaseTimer(io.datarouter.util.timer.PhaseTimer) HtmlForm(io.datarouter.web.html.form.HtmlForm) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) ParallelScannerContext(io.datarouter.scanner.ParallelScannerContext) CallableTool(io.datarouter.util.concurrent.CallableTool) ExecutorService(java.util.concurrent.ExecutorService) BaseHandler(io.datarouter.web.handler.BaseHandler)

Example 2 with StringTool

use of io.datarouter.util.string.StringTool in project datarouter by hotpads.

the class JobletCopyTableHandler method defaultHandler.

@Handler(defaultHandler = true)
private <PK extends PrimaryKey<PK>, D extends Databean<PK, D>> Mav defaultHandler(@Param(P_sourceNodeName) OptionalString sourceNodeName, @Param(P_targetNodeName) OptionalString targetNodeName, @Param(P_putBatchSize) OptionalString putBatchSize, @Param(P_submitAction) OptionalString submitAction) {
    String errorPutBatchSize = null;
    if (submitAction.isPresent()) {
        try {
            if (putBatchSize.map(StringTool::nullIfEmpty).isPresent()) {
                Integer.valueOf(putBatchSize.get());
            }
        } catch (Exception e) {
            errorPutBatchSize = "Please specify an integer";
        }
    }
    List<String> possibleNodes = tableSamplerService.scanCountableNodes().map(node -> node.getClientId().getName() + "." + node.getFieldInfo().getTableName()).append("").sort().list();
    var form = new HtmlForm().withMethod("post");
    form.addSelectField().withDisplay("Source Node Name").withName(P_sourceNodeName).withValues(possibleNodes);
    form.addSelectField().withDisplay("Target Node Name").withName(P_targetNodeName).withValues(possibleNodes);
    form.addTextField().withDisplay("Batch Size").withError(errorPutBatchSize).withName(P_putBatchSize).withPlaceholder(DEFAULT_BATCH_SIZE + "").withValue(putBatchSize.orElse(null));
    form.addButton().withDisplay("Create Joblets").withValue("anything");
    if (submitAction.isEmpty() || form.hasErrors()) {
        return pageFactory.startBuilder(request).withTitle("Copy Table - Joblets").withContent(Html.makeContent(form)).buildMav();
    }
    @SuppressWarnings("unchecked") PhysicalSortedStorageNode<PK, D, ?> sourceNode = (PhysicalSortedStorageNode<PK, D, ?>) nodes.getNode(sourceNodeName.get());
    String tableName = sourceNode.getFieldInfo().getTableName();
    List<TableSample> samples = tableSamplerService.scanSamplesForNode(sourceNode).list();
    TableSampleKey previousSampleKey = null;
    List<JobletPackage> jobletPackages = new ArrayList<>();
    // +1 for databeans beyond the final sample
    long numJoblets = samples.size() + 1;
    long counter = 1;
    int batchSize = putBatchSize.map(StringTool::nullIfEmpty).map(Integer::valueOf).orElse(DEFAULT_BATCH_SIZE);
    for (TableSample sample : samples) {
        PK fromKeyExclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, previousSampleKey);
        PK toKeyInclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, sample.getKey());
        jobletPackages.add(createJobletPackage(tableName, sourceNodeName.get(), targetNodeName.get(), fromKeyExclusive, toKeyInclusive, batchSize, sample.getNumRows(), counter, numJoblets));
        ++counter;
        previousSampleKey = sample.getKey();
    }
    // include any rows created since the last sample
    PK fromKeyExclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, previousSampleKey);
    jobletPackages.add(createJobletPackage(tableName, sourceNodeName.get(), targetNodeName.get(), fromKeyExclusive, // open-ended
    null, batchSize, // we have no idea about the true estNumDatabeans
    1, counter, numJoblets));
    ++counter;
    // shuffle as optimization to spread write load.  could be optional
    Scanner.of(jobletPackages).shuffle().flush(jobletService::submitJobletPackages);
    changelogRecorderService.recordChangelog(getSessionInfo(), "Joblet", sourceNodeName.get(), targetNodeName.get());
    return pageFactory.message(request, "created " + numJoblets + " joblets");
}
Also used : JobletService(io.datarouter.joblet.service.JobletService) Scanner(io.datarouter.scanner.Scanner) JobletPackage(io.datarouter.joblet.model.JobletPackage) TableSamplerTool(io.datarouter.nodewatch.util.TableSamplerTool) PrimaryKeyPercentCodecTool(io.datarouter.storage.util.PrimaryKeyPercentCodecTool) TableSample(io.datarouter.nodewatch.storage.tablesample.TableSample) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TableSampleKey(io.datarouter.nodewatch.storage.tablesample.TableSampleKey) TagCreator.h2(j2html.TagCreator.h2) ArrayList(java.util.ArrayList) Inject(javax.inject.Inject) TagCreator.br(j2html.TagCreator.br) DatarouterNodes(io.datarouter.storage.node.DatarouterNodes) Param(io.datarouter.web.handler.types.Param) Bootstrap4FormHtml(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml) JobletPriority(io.datarouter.joblet.enums.JobletPriority) PhysicalSortedStorageNode(io.datarouter.storage.node.op.raw.SortedStorage.PhysicalSortedStorageNode) TableSamplerService(io.datarouter.nodewatch.service.TableSamplerService) Mav(io.datarouter.web.handler.mav.Mav) StringTool(io.datarouter.util.string.StringTool) PrimaryKey(io.datarouter.model.key.primary.PrimaryKey) ContainerTag(j2html.tags.ContainerTag) CopyTableJoblet(io.datarouter.plugin.copytable.CopyTableJoblet) List(java.util.List) HtmlForm(io.datarouter.web.html.form.HtmlForm) Databean(io.datarouter.model.databean.Databean) BaseHandler(io.datarouter.web.handler.BaseHandler) CopyTableJobletParams(io.datarouter.plugin.copytable.CopyTableJoblet.CopyTableJobletParams) Bootstrap4PageFactory(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory) TagCreator.div(j2html.TagCreator.div) StringTool(io.datarouter.util.string.StringTool) ArrayList(java.util.ArrayList) TableSample(io.datarouter.nodewatch.storage.tablesample.TableSample) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TableSampleKey(io.datarouter.nodewatch.storage.tablesample.TableSampleKey) PhysicalSortedStorageNode(io.datarouter.storage.node.op.raw.SortedStorage.PhysicalSortedStorageNode) HtmlForm(io.datarouter.web.html.form.HtmlForm) JobletPackage(io.datarouter.joblet.model.JobletPackage) BaseHandler(io.datarouter.web.handler.BaseHandler)

Example 3 with StringTool

use of io.datarouter.util.string.StringTool in project datarouter by hotpads.

the class JobletTableProcessorHandler method defaultHandler.

@Handler(defaultHandler = true)
private <PK extends PrimaryKey<PK>, D extends Databean<PK, D>> Mav defaultHandler(@Param(P_nodeName) OptionalString nodeName, @Param(P_scanBatchSize) OptionalString scanBatchSize, @Param(P_processorName) OptionalString processorName, @Param(P_submitAction) OptionalString submitAction) {
    String errorScanBatchSize = null;
    if (submitAction.isPresent()) {
        try {
            if (scanBatchSize.map(StringTool::nullIfEmpty).isPresent()) {
                Integer.valueOf(scanBatchSize.get());
            }
        } catch (Exception e) {
            errorScanBatchSize = "Please specify an integer";
        }
    }
    List<String> possibleNodes = tableSamplerService.scanCountableNodes().map(node -> node.getClientId().getName() + "." + node.getFieldInfo().getTableName()).append("").sort().list();
    List<String> possibleProcessors = Scanner.of(processorRegistry.getAll()).map(Class::getSimpleName).append("").sort().list();
    var form = new HtmlForm().withMethod("post");
    form.addSelectField().withDisplay("Node Name").withName(P_nodeName).withValues(possibleNodes);
    form.addTextField().withDisplay("Scan Batch Size").withError(errorScanBatchSize).withName(P_scanBatchSize).withPlaceholder(DEFAULT_SCAN_BATCH_SIZE + "").withValue(scanBatchSize.orElse(null));
    form.addSelectField().withDisplay("Processor Name").withName(P_processorName).withValues(possibleProcessors);
    form.addButton().withDisplay("Create Joblets").withValue("anything");
    if (submitAction.isEmpty() || form.hasErrors()) {
        return pageFactory.startBuilder(request).withTitle("Table Processor - Joblets").withContent(Html.makeContent(form)).buildMav();
    }
    @SuppressWarnings("unchecked") PhysicalSortedStorageNode<PK, D, ?> sourceNode = (PhysicalSortedStorageNode<PK, D, ?>) nodes.getNode(nodeName.get());
    String tableName = sourceNode.getFieldInfo().getTableName();
    List<TableSample> samples = tableSamplerService.scanSamplesForNode(sourceNode).list();
    TableSampleKey previousSampleKey = null;
    List<JobletPackage> jobletPackages = new ArrayList<>();
    long totalItemsProcessed = 1;
    long counter = 1;
    int actualScanBatchSize = scanBatchSize.map(StringTool::nullIfEmpty).map(Integer::valueOf).orElse(DEFAULT_SCAN_BATCH_SIZE);
    long numJoblets = 0;
    for (TableSample sample : samples) {
        PK fromKeyExclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, previousSampleKey);
        PK toKeyInclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, sample.getKey());
        var jobletPackage = createJobletPackage(tableName, nodeName.get(), fromKeyExclusive, toKeyInclusive, actualScanBatchSize, processorName.get(), sample.getNumRows(), counter, numJoblets);
        jobletPackages.add(jobletPackage);
        ++numJoblets;
        counter++;
        totalItemsProcessed++;
        previousSampleKey = sample.getKey();
    }
    // include any rows created since the last sample
    PK fromKeyExclusive = TableSamplerTool.extractPrimaryKeyFromSampleKey(sourceNode, previousSampleKey);
    var jobletPackage = createJobletPackage(tableName, nodeName.get(), fromKeyExclusive, // open-ended
    null, actualScanBatchSize, processorName.get(), // we have no idea about the true estNumDatabeans
    1, counter, numJoblets);
    ++numJoblets;
    jobletPackages.add(jobletPackage);
    totalItemsProcessed++;
    // jobletPackage.size() == counter == numJoblets
    counter++;
    // shuffle as optimization to spread write load. could be optional
    Scanner.of(jobletPackages).shuffle().flush(jobletService::submitJobletPackages);
    changelogRecorderService.recordChangelogForTableProcessor(getSessionInfo(), "Joblet", nodeName.get(), processorName.get());
    return pageFactory.message(request, "jobletsCreated=" + numJoblets + " totalSamplesProcessed=" + totalItemsProcessed);
}
Also used : JobletService(io.datarouter.joblet.service.JobletService) Scanner(io.datarouter.scanner.Scanner) JobletPackage(io.datarouter.joblet.model.JobletPackage) TableSamplerTool(io.datarouter.nodewatch.util.TableSamplerTool) PrimaryKeyPercentCodecTool(io.datarouter.storage.util.PrimaryKeyPercentCodecTool) TableSample(io.datarouter.nodewatch.storage.tablesample.TableSample) TableProcessorJobletParams(io.datarouter.plugin.copytable.tableprocessor.TableProcessorJoblet.TableProcessorJobletParams) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TableSampleKey(io.datarouter.nodewatch.storage.tablesample.TableSampleKey) TagCreator.h2(j2html.TagCreator.h2) ArrayList(java.util.ArrayList) Inject(javax.inject.Inject) TagCreator.br(j2html.TagCreator.br) Config(io.datarouter.storage.config.Config) DatarouterNodes(io.datarouter.storage.node.DatarouterNodes) Param(io.datarouter.web.handler.types.Param) Bootstrap4FormHtml(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml) JobletPriority(io.datarouter.joblet.enums.JobletPriority) PhysicalSortedStorageNode(io.datarouter.storage.node.op.raw.SortedStorage.PhysicalSortedStorageNode) TableSamplerService(io.datarouter.nodewatch.service.TableSamplerService) TableProcessorRegistry(io.datarouter.plugin.copytable.tableprocessor.TableProcessorRegistry) Mav(io.datarouter.web.handler.mav.Mav) StringTool(io.datarouter.util.string.StringTool) PrimaryKey(io.datarouter.model.key.primary.PrimaryKey) ContainerTag(j2html.tags.ContainerTag) List(java.util.List) HtmlForm(io.datarouter.web.html.form.HtmlForm) Databean(io.datarouter.model.databean.Databean) TableProcessorJoblet(io.datarouter.plugin.copytable.tableprocessor.TableProcessorJoblet) BaseHandler(io.datarouter.web.handler.BaseHandler) Bootstrap4PageFactory(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory) TagCreator.div(j2html.TagCreator.div) StringTool(io.datarouter.util.string.StringTool) ArrayList(java.util.ArrayList) TableSample(io.datarouter.nodewatch.storage.tablesample.TableSample) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TableSampleKey(io.datarouter.nodewatch.storage.tablesample.TableSampleKey) PhysicalSortedStorageNode(io.datarouter.storage.node.op.raw.SortedStorage.PhysicalSortedStorageNode) HtmlForm(io.datarouter.web.html.form.HtmlForm) JobletPackage(io.datarouter.joblet.model.JobletPackage) BaseHandler(io.datarouter.web.handler.BaseHandler)

Example 4 with StringTool

use of io.datarouter.util.string.StringTool in project datarouter by hotpads.

the class SingleThreadCopyTableHandler method defaultHandler.

@Handler(defaultHandler = true)
private <PK extends PrimaryKey<PK>, D extends Databean<PK, D>> Mav defaultHandler(@Param(P_sourceNodeName) OptionalString sourceNodeName, @Param(P_targetNodeName) OptionalString targetNodeName, @Param(P_lastKeyString) OptionalString lastKeyString, @Param(P_toEmail) OptionalString toEmail, @Param(P_numThreads) OptionalString numThreads, @Param(P_putBatchSize) OptionalString putBatchSize, @Param(P_submitAction) OptionalString submitAction) {
    String errorNumThreads = null;
    String errorPutBatchSize = null;
    if (submitAction.isPresent()) {
        try {
            if (numThreads.map(StringTool::nullIfEmpty).isPresent()) {
                Integer.valueOf(numThreads.get());
            }
        } catch (Exception e) {
            errorNumThreads = "Please specify an integer";
        }
        try {
            if (putBatchSize.map(StringTool::nullIfEmpty).isPresent()) {
                Integer.valueOf(putBatchSize.get());
            }
        } catch (Exception e) {
            errorPutBatchSize = "Please specify an integer";
        }
    }
    List<String> possibleSourceNodes = tableSamplerService.scanAllSortedMapStorageNodes().map(node -> node.getClientId().getName() + "." + node.getFieldInfo().getTableName()).append("").sort().list();
    List<String> possibleTargetNodes = tableSamplerService.scanCountableNodes().map(node -> node.getClientId().getName() + "." + node.getFieldInfo().getTableName()).append("").sort().list();
    var form = new HtmlForm().withMethod("post");
    form.addSelectField().withDisplay("Source Node Name").withName(P_sourceNodeName).withValues(possibleSourceNodes);
    form.addSelectField().withDisplay("Target Node Name").withName(P_targetNodeName).withValues(possibleTargetNodes);
    form.addTextField().withDisplay("Last Key String").withName(P_lastKeyString).withValue(lastKeyString.orElse(null));
    form.addTextField().withDisplay("Num Threads").withError(errorNumThreads).withName(P_numThreads).withPlaceholder(DEFAULT_NUM_THREADS + "").withValue(numThreads.orElse(null));
    form.addTextField().withDisplay("Batch Size").withError(errorPutBatchSize).withName(P_putBatchSize).withPlaceholder(DEFAULT_BATCH_SIZE + "").withValue(putBatchSize.orElse(null));
    form.addTextField().withDisplay("Email on Completion").withName(P_toEmail).withPlaceholder("you@email.com").withValue(toEmail.orElse(null));
    form.addButton().withDisplay("Copy").withValue("anything");
    if (submitAction.isEmpty() || form.hasErrors()) {
        return pageFactory.startBuilder(request).withTitle("Copy Table - Single Thread").withContent(Html.makeContent(form)).buildMav();
    }
    int actualNumThreads = numThreads.map(StringTool::nullIfEmpty).map(Integer::valueOf).orElse(DEFAULT_NUM_THREADS);
    int actualPutBatchSize = putBatchSize.map(StringTool::nullIfEmpty).map(Integer::valueOf).orElse(DEFAULT_BATCH_SIZE);
    CopyTableSpanResult result = copyTableService.copyTableSpan(sourceNodeName.get(), targetNodeName.get(), lastKeyString.map(StringTool::nullIfEmpty).orElse(null), null, actualNumThreads, actualPutBatchSize, 1, 1);
    if (!result.success) {
        String message = String.format("The migration was interrupted unexpectedly with %s." + "  Please resume the migration with lastKey %s", result.exception.getMessage(), result.resumeFromKeyString);
        return pageFactory.message(request, message);
    }
    var header = standardDatarouterEmailHeaderService.makeStandardHeader();
    String message = String.format("Successfully migrated %s records from %s to %s", NumberFormatter.addCommas(result.numCopied), sourceNodeName.get(), targetNodeName.get());
    var body = body(header, p(message));
    if (toEmail.filter(str -> !str.isEmpty()).isPresent()) {
        String primaryHref = htmlEmailService.startLinkBuilder().withLocalPath(paths.datarouter.copyTableSingleThread).build();
        var emailBuilder = htmlEmailService.startEmailBuilder().withTitle("Copy Table").withTitleHref(primaryHref).withContent(body).fromAdmin().to(toEmail.get());
        htmlEmailService.trySendJ2Html(emailBuilder);
    }
    changelogRecorderService.recordChangelog(getSessionInfo(), "Single Thread", sourceNodeName.get(), targetNodeName.get());
    return pageFactory.message(request, message);
}
Also used : TagCreator.body(j2html.TagCreator.body) DatarouterHtmlEmailService(io.datarouter.web.email.DatarouterHtmlEmailService) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TagCreator.h2(j2html.TagCreator.h2) Inject(javax.inject.Inject) NumberFormatter(io.datarouter.util.number.NumberFormatter) TagCreator.br(j2html.TagCreator.br) Param(io.datarouter.web.handler.types.Param) Bootstrap4FormHtml(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml) CopyTableService(io.datarouter.plugin.copytable.CopyTableService) TagCreator.p(j2html.TagCreator.p) TableSamplerService(io.datarouter.nodewatch.service.TableSamplerService) CopyTableSpanResult(io.datarouter.plugin.copytable.CopyTableService.CopyTableSpanResult) StandardDatarouterEmailHeaderService(io.datarouter.web.email.StandardDatarouterEmailHeaderService) Mav(io.datarouter.web.handler.mav.Mav) StringTool(io.datarouter.util.string.StringTool) PrimaryKey(io.datarouter.model.key.primary.PrimaryKey) ContainerTag(j2html.tags.ContainerTag) List(java.util.List) HtmlForm(io.datarouter.web.html.form.HtmlForm) Databean(io.datarouter.model.databean.Databean) BaseHandler(io.datarouter.web.handler.BaseHandler) Bootstrap4PageFactory(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory) DatarouterCopyTablePaths(io.datarouter.plugin.copytable.config.DatarouterCopyTablePaths) TagCreator.div(j2html.TagCreator.div) HtmlForm(io.datarouter.web.html.form.HtmlForm) StringTool(io.datarouter.util.string.StringTool) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) CopyTableSpanResult(io.datarouter.plugin.copytable.CopyTableService.CopyTableSpanResult) BaseHandler(io.datarouter.web.handler.BaseHandler)

Example 5 with StringTool

use of io.datarouter.util.string.StringTool in project datarouter by hotpads.

the class SingleThreadTableProcessorHandler method defaultHandler.

@Handler(defaultHandler = true)
private <PK extends PrimaryKey<PK>, D extends Databean<PK, D>> Mav defaultHandler(@Param(P_sourceNodeName) OptionalString sourceName, @Param(P_lastKeyString) OptionalString lastKeyString, @Param(P_scanBatchSize) OptionalString scanBatchSize, @Param(P_processorName) OptionalString processorName, @Param(P_toEmail) OptionalString toEmail, @Param(P_submitAction) OptionalString submitAction) {
    String errorScanBatchSize = null;
    if (submitAction.isPresent()) {
        try {
            if (scanBatchSize.map(StringTool::nullIfEmpty).isPresent()) {
                Integer.valueOf(scanBatchSize.get());
            }
        } catch (Exception e) {
            errorScanBatchSize = "Please specify an integer";
        }
    }
    List<String> possibleNodes = tableSamplerService.scanAllSortedMapStorageNodes().map(node -> node.getClientId().getName() + "." + node.getFieldInfo().getTableName()).append("").sort().list();
    List<String> possibleProcessors = Scanner.of(processorRegistry.getAll()).map(Class::getSimpleName).sort().list();
    var form = new HtmlForm().withMethod("post");
    form.addSelectField().withDisplay("Node Name").withName(P_sourceNodeName).withValues(possibleNodes);
    form.addTextField().withDisplay("From Key String").withName(P_lastKeyString).withValue(lastKeyString.orElse(null));
    form.addTextField().withDisplay("Scan Batch Size").withError(errorScanBatchSize).withName(P_scanBatchSize).withPlaceholder(DEFAULT_SCAN_BATCH_SIZE + "").withValue(scanBatchSize.orElse(null));
    form.addSelectField().withDisplay("Processor Name").withName(P_processorName).withValues(possibleProcessors);
    form.addTextField().withDisplay("Email on Completion").withName(P_toEmail).withPlaceholder("you@email.com").withValue(toEmail.orElse(null));
    form.addButton().withDisplay("Copy").withValue("anything");
    if (submitAction.isEmpty() || form.hasErrors()) {
        return pageFactory.startBuilder(request).withTitle("Table Processor - Single Thread").withContent(Html.makeContent(form)).buildMav();
    }
    int actualScanBatchSize = scanBatchSize.map(StringTool::nullIfEmpty).map(Integer::valueOf).orElse(DEFAULT_SCAN_BATCH_SIZE);
    TableProcessor<?, ?> processor = injector.getInstance(processorRegistry.find(processorName.get()).get());
    TableProcessorSpanResult result = service.runTableProcessor(sourceName.get(), lastKeyString.map(StringTool::nullIfEmpty).orElse(null), null, actualScanBatchSize, processor, 1, 1);
    if (!result.success) {
        String message = String.format("The table processor was interrupted unexpectedly with %s." + "  Please resume the processor with lastKey %s", result.exception.getMessage(), result.resumeFromKeyString);
        return pageFactory.message(request, message);
    }
    var header = standardDatarouterEmailHeaderService.makeStandardHeader();
    String message = String.format("Successfully processed %s records for %s - %s", NumberFormatter.addCommas(result.numScanned), sourceName.get(), processorName.get());
    var body = body(header, p(message));
    if (toEmail.filter(str -> !str.isEmpty()).isPresent()) {
        String primaryHref = htmlEmailService.startLinkBuilder().withLocalPath(paths.datarouter.copyTableSingleThread).build();
        var emailBuilder = htmlEmailService.startEmailBuilder().withTitle("Table Processor").withTitleHref(primaryHref).withContent(body).fromAdmin().to(toEmail.get());
        htmlEmailService.trySendJ2Html(emailBuilder);
    }
    changelogRecorderService.recordChangelogForTableProcessor(getSessionInfo(), "Single Thread", sourceName.get(), processorName.get());
    return pageFactory.message(request, message);
}
Also used : Scanner(io.datarouter.scanner.Scanner) TagCreator.body(j2html.TagCreator.body) DatarouterHtmlEmailService(io.datarouter.web.email.DatarouterHtmlEmailService) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TagCreator.h2(j2html.TagCreator.h2) TableProcessorService(io.datarouter.plugin.copytable.tableprocessor.TableProcessorService) Inject(javax.inject.Inject) NumberFormatter(io.datarouter.util.number.NumberFormatter) TagCreator.br(j2html.TagCreator.br) Config(io.datarouter.storage.config.Config) Param(io.datarouter.web.handler.types.Param) Bootstrap4FormHtml(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml) DatarouterInjector(io.datarouter.inject.DatarouterInjector) TagCreator.p(j2html.TagCreator.p) TableSamplerService(io.datarouter.nodewatch.service.TableSamplerService) TableProcessorRegistry(io.datarouter.plugin.copytable.tableprocessor.TableProcessorRegistry) StandardDatarouterEmailHeaderService(io.datarouter.web.email.StandardDatarouterEmailHeaderService) Mav(io.datarouter.web.handler.mav.Mav) StringTool(io.datarouter.util.string.StringTool) PrimaryKey(io.datarouter.model.key.primary.PrimaryKey) ContainerTag(j2html.tags.ContainerTag) TableProcessorSpanResult(io.datarouter.plugin.copytable.tableprocessor.TableProcessorService.TableProcessorSpanResult) List(java.util.List) TableProcessor(io.datarouter.plugin.copytable.tableprocessor.TableProcessor) HtmlForm(io.datarouter.web.html.form.HtmlForm) Databean(io.datarouter.model.databean.Databean) BaseHandler(io.datarouter.web.handler.BaseHandler) Bootstrap4PageFactory(io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory) DatarouterCopyTablePaths(io.datarouter.plugin.copytable.config.DatarouterCopyTablePaths) TagCreator.div(j2html.TagCreator.div) HtmlForm(io.datarouter.web.html.form.HtmlForm) StringTool(io.datarouter.util.string.StringTool) OptionalString(io.datarouter.web.handler.types.optional.OptionalString) TableProcessorSpanResult(io.datarouter.plugin.copytable.tableprocessor.TableProcessorService.TableProcessorSpanResult) BaseHandler(io.datarouter.web.handler.BaseHandler)

Aggregations

StringTool (io.datarouter.util.string.StringTool)8 BaseHandler (io.datarouter.web.handler.BaseHandler)7 Mav (io.datarouter.web.handler.mav.Mav)7 OptionalString (io.datarouter.web.handler.types.optional.OptionalString)7 HtmlForm (io.datarouter.web.html.form.HtmlForm)7 Bootstrap4FormHtml (io.datarouter.web.html.j2html.bootstrap4.Bootstrap4FormHtml)7 Bootstrap4PageFactory (io.datarouter.web.html.j2html.bootstrap4.Bootstrap4PageFactory)7 TagCreator.div (j2html.TagCreator.div)7 List (java.util.List)7 Inject (javax.inject.Inject)7 Scanner (io.datarouter.scanner.Scanner)6 Param (io.datarouter.web.handler.types.Param)6 TagCreator.br (j2html.TagCreator.br)6 TagCreator.h2 (j2html.TagCreator.h2)6 ContainerTag (j2html.tags.ContainerTag)6 Databean (io.datarouter.model.databean.Databean)4 PrimaryKey (io.datarouter.model.key.primary.PrimaryKey)4 TableSamplerService (io.datarouter.nodewatch.service.TableSamplerService)4 NumberFormatter (io.datarouter.util.number.NumberFormatter)4 Config (io.datarouter.storage.config.Config)3