mobbdev 0.0.92 → 0.0.93

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/index.mjs +153 -103
  2. package/package.json +1 -1
package/dist/index.mjs CHANGED
@@ -104,6 +104,12 @@ var errorMessages = {
104
104
  "(--token)"
105
105
  )} is needed if you're adding an SCM token`
106
106
  };
107
+ var progressMassages = {
108
+ processingVulnerabilityReportSuccess: "\u2699\uFE0F Vulnerability report proccessed successfully",
109
+ processingVulnerabilityReport: "\u2699\uFE0F Proccessing vulnerability report",
110
+ processingVulnerabilityReportFailed: "\u2699\uFE0F Error Proccessing vulnerability report"
111
+ };
112
+ var VUL_REPORT_DIGEST_TIMEOUT_MS = 1e3 * 60 * 20;
107
113
 
108
114
  // src/features/analysis/index.ts
109
115
  import crypto from "node:crypto";
@@ -179,7 +185,7 @@ var CliError = class extends Error {
179
185
  // src/features/analysis/index.ts
180
186
  import chalk4 from "chalk";
181
187
  import Configstore from "configstore";
182
- import Debug10 from "debug";
188
+ import Debug11 from "debug";
183
189
  import extract from "extract-zip";
184
190
  import fetch3 from "node-fetch";
185
191
  import open2 from "open";
@@ -563,7 +569,7 @@ var GET_VUL_BY_NODES_METADATA = gql2`
563
569
  // src/features/analysis/graphql/subscirbe.ts
564
570
  import { createClient } from "graphql-ws";
565
571
  import WebSocket from "ws";
566
- var SUBSCRIPTION_TIMEOUT_MS = 5 * 60 * 1e3;
572
+ var SUBSCRIPTION_TIMEOUT_MS = 10 * 60 * 1e3;
567
573
  function createWSClient(options) {
568
574
  return createClient({
569
575
  url: options.url,
@@ -1044,22 +1050,24 @@ var GQLClient = class {
1044
1050
  res
1045
1051
  ).vulnerability_report_path.map((p) => p.path);
1046
1052
  }
1047
- async subscribeToAnalysis(params, callback) {
1053
+ async subscribeToAnalysis(params) {
1054
+ const { callbackStates } = params;
1048
1055
  return subscribe(
1049
1056
  SUBSCRIBE_TO_ANALYSIS,
1050
- params,
1057
+ params.subscribeToAnalysisParams,
1051
1058
  async (resolve, reject, data) => {
1052
1059
  if (data.analysis.state === "Failed") {
1053
1060
  reject(data);
1054
1061
  throw new Error(`Analysis failed with id: ${data.analysis.id}`);
1055
1062
  }
1056
- if (data.analysis?.state === "Finished") {
1057
- await callback(data.analysis.id);
1063
+ if (callbackStates.includes(data.analysis?.state)) {
1064
+ await params.callback(data.analysis.id);
1058
1065
  resolve(data);
1059
1066
  }
1060
1067
  },
1061
1068
  {
1062
- apiKey: this._apiKey
1069
+ apiKey: this._apiKey,
1070
+ timeoutInMs: params.timeoutInMs
1063
1071
  }
1064
1072
  );
1065
1073
  }
@@ -1091,7 +1099,7 @@ var GQLClient = class {
1091
1099
 
1092
1100
  // src/features/analysis/handle_finished_analysis.ts
1093
1101
  import { Octokit as Octokit3 } from "@octokit/core";
1094
- import Debug4 from "debug";
1102
+ import Debug5 from "debug";
1095
1103
  import parseDiff from "parse-diff";
1096
1104
  import { z as z10 } from "zod";
1097
1105
 
@@ -3700,8 +3708,42 @@ function calculateRanges(integers) {
3700
3708
  return ranges;
3701
3709
  }
3702
3710
 
3711
+ // src/features/analysis/utils/send_report.ts
3712
+ import Debug4 from "debug";
3713
+ var debug4 = Debug4("mobbdev:index");
3714
+ async function sendReport({
3715
+ spinner,
3716
+ submitVulnerabilityReportVariables,
3717
+ gqlClient
3718
+ }) {
3719
+ try {
3720
+ const sumbitRes = await gqlClient.submitVulnerabilityReport(
3721
+ submitVulnerabilityReportVariables
3722
+ );
3723
+ if (sumbitRes.submitVulnerabilityReport.__typename !== "VulnerabilityReport") {
3724
+ debug4("error submit vul report %s", sumbitRes);
3725
+ throw new Error("\u{1F575}\uFE0F\u200D\u2642\uFE0F Mobb analysis failed");
3726
+ }
3727
+ spinner.update({ text: progressMassages.processingVulnerabilityReport });
3728
+ await gqlClient.subscribeToAnalysis({
3729
+ subscribeToAnalysisParams: {
3730
+ analysisId: sumbitRes.submitVulnerabilityReport.fixReportId
3731
+ },
3732
+ callback: () => spinner.update({
3733
+ text: "\u2699\uFE0F Vulnerability report proccessed successfuly"
3734
+ }),
3735
+ callbackStates: ["Digested", "Finished"],
3736
+ timeoutInMs: VUL_REPORT_DIGEST_TIMEOUT_MS
3737
+ });
3738
+ return sumbitRes;
3739
+ } catch (e) {
3740
+ spinner.error({ text: "\u{1F575}\uFE0F\u200D\u2642\uFE0F Mobb analysis failed" });
3741
+ throw e;
3742
+ }
3743
+ }
3744
+
3703
3745
  // src/features/analysis/handle_finished_analysis.ts
3704
- var debug4 = Debug4("mobbdev:handle-finished-analysis");
3746
+ var debug5 = Debug5("mobbdev:handle-finished-analysis");
3705
3747
  var contactUsMarkdown = `For specific requests [contact us](https://mobb.ai/contact) and we'll do the most to answer your need quickly.`;
3706
3748
  var commitFixButton = (commitUrl) => `<a href="${commitUrl}"><img src=${COMMIT_FIX_SVG}></a>`;
3707
3749
  var MobbIconMarkdown = `![image](${MOBB_ICON_IMG})`;
@@ -3839,7 +3881,7 @@ async function handleFinishedAnalysis({
3839
3881
  { authToken: githubActionToken }
3840
3882
  );
3841
3883
  } catch (e) {
3842
- debug4("delete comment failed %s", e);
3884
+ debug5("delete comment failed %s", e);
3843
3885
  return Promise.resolve();
3844
3886
  }
3845
3887
  });
@@ -3854,7 +3896,7 @@ async function handleFinishedAnalysis({
3854
3896
  githubActionOctokit
3855
3897
  );
3856
3898
  } catch (e) {
3857
- debug4("delete comment failed %s", e);
3899
+ debug5("delete comment failed %s", e);
3858
3900
  return Promise.resolve();
3859
3901
  }
3860
3902
  });
@@ -3935,7 +3977,7 @@ ${fixPageLink}`,
3935
3977
  fixablePrVuls,
3936
3978
  nonFixablePrVuls
3937
3979
  } = prVulenrabilities;
3938
- debug4({
3980
+ debug5({
3939
3981
  fixablePrVuls,
3940
3982
  nonFixablePrVuls,
3941
3983
  vulnerabilitiesOutsidePr,
@@ -4011,10 +4053,10 @@ ${contactUsMarkdown}`;
4011
4053
  import fs2 from "node:fs";
4012
4054
  import path4 from "node:path";
4013
4055
  import AdmZip from "adm-zip";
4014
- import Debug5 from "debug";
4056
+ import Debug6 from "debug";
4015
4057
  import { globby } from "globby";
4016
4058
  import { isBinary } from "istextorbinary";
4017
- var debug5 = Debug5("mobbdev:pack");
4059
+ var debug6 = Debug6("mobbdev:pack");
4018
4060
  var MAX_FILE_SIZE = 1024 * 1024 * 5;
4019
4061
  function endsWithAny(str, suffixes) {
4020
4062
  return suffixes.some(function(suffix) {
@@ -4022,37 +4064,37 @@ function endsWithAny(str, suffixes) {
4022
4064
  });
4023
4065
  }
4024
4066
  async function pack(srcDirPath, vulnFiles) {
4025
- debug5("pack folder %s", srcDirPath);
4067
+ debug6("pack folder %s", srcDirPath);
4026
4068
  const filepaths = await globby("**", {
4027
4069
  gitignore: true,
4028
4070
  onlyFiles: true,
4029
4071
  cwd: srcDirPath,
4030
4072
  followSymbolicLinks: false
4031
4073
  });
4032
- debug5("files found %d", filepaths.length);
4074
+ debug6("files found %d", filepaths.length);
4033
4075
  const zip = new AdmZip();
4034
- debug5("compressing files");
4076
+ debug6("compressing files");
4035
4077
  for (const filepath of filepaths) {
4036
4078
  const absFilepath = path4.join(srcDirPath, filepath.toString());
4037
4079
  if (!endsWithAny(
4038
4080
  absFilepath.toString().replaceAll(path4.win32.sep, path4.posix.sep),
4039
4081
  vulnFiles
4040
4082
  )) {
4041
- debug5("ignoring %s because it is not a vulnerability file", filepath);
4083
+ debug6("ignoring %s because it is not a vulnerability file", filepath);
4042
4084
  continue;
4043
4085
  }
4044
4086
  if (fs2.lstatSync(absFilepath).size > MAX_FILE_SIZE) {
4045
- debug5("ignoring %s because the size is > 5MB", filepath);
4087
+ debug6("ignoring %s because the size is > 5MB", filepath);
4046
4088
  continue;
4047
4089
  }
4048
4090
  const data = fs2.readFileSync(absFilepath);
4049
4091
  if (isBinary(null, data)) {
4050
- debug5("ignoring %s because is seems to be a binary file", filepath);
4092
+ debug6("ignoring %s because is seems to be a binary file", filepath);
4051
4093
  continue;
4052
4094
  }
4053
4095
  zip.addFile(filepath.toString(), data);
4054
4096
  }
4055
- debug5("get zip file buffer");
4097
+ debug6("get zip file buffer");
4056
4098
  return zip.toBuffer();
4057
4099
  }
4058
4100
 
@@ -4127,7 +4169,7 @@ var cxOperatingSystemSupportMessage = `Your operating system does not support ch
4127
4169
 
4128
4170
  // src/utils/child_process.ts
4129
4171
  import cp from "node:child_process";
4130
- import Debug6 from "debug";
4172
+ import Debug7 from "debug";
4131
4173
  import * as process2 from "process";
4132
4174
  import supportsColor from "supports-color";
4133
4175
  var { stdout: stdout2 } = supportsColor;
@@ -4146,16 +4188,16 @@ function createSpwan({ args, processPath, name }, options) {
4146
4188
  return createChildProcess({ childProcess: child, name }, options);
4147
4189
  }
4148
4190
  function createChildProcess({ childProcess, name }, options) {
4149
- const debug10 = Debug6(`mobbdev:${name}`);
4191
+ const debug11 = Debug7(`mobbdev:${name}`);
4150
4192
  const { display } = options;
4151
4193
  return new Promise((resolve, reject) => {
4152
4194
  let out = "";
4153
4195
  const onData = (chunk) => {
4154
- debug10(`chunk received from ${name} std ${chunk}`);
4196
+ debug11(`chunk received from ${name} std ${chunk}`);
4155
4197
  out += chunk;
4156
4198
  };
4157
4199
  if (!childProcess || !childProcess?.stdout || !childProcess?.stderr) {
4158
- debug10(`unable to fork ${name}`);
4200
+ debug11(`unable to fork ${name}`);
4159
4201
  reject(new Error(`unable to fork ${name}`));
4160
4202
  }
4161
4203
  childProcess.stdout?.on("data", onData);
@@ -4165,11 +4207,11 @@ function createChildProcess({ childProcess, name }, options) {
4165
4207
  childProcess.stderr?.pipe(process2.stderr);
4166
4208
  }
4167
4209
  childProcess.on("exit", (code) => {
4168
- debug10(`${name} exit code ${code}`);
4210
+ debug11(`${name} exit code ${code}`);
4169
4211
  resolve({ message: out, code });
4170
4212
  });
4171
4213
  childProcess.on("error", (err) => {
4172
- debug10(`${name} error %o`, err);
4214
+ debug11(`${name} error %o`, err);
4173
4215
  reject(err);
4174
4216
  });
4175
4217
  });
@@ -4177,12 +4219,12 @@ function createChildProcess({ childProcess, name }, options) {
4177
4219
 
4178
4220
  // src/features/analysis/scanners/checkmarx.ts
4179
4221
  import chalk2 from "chalk";
4180
- import Debug7 from "debug";
4222
+ import Debug8 from "debug";
4181
4223
  import { existsSync } from "fs";
4182
4224
  import { createSpinner as createSpinner2 } from "nanospinner";
4183
4225
  import { type } from "os";
4184
4226
  import path5 from "path";
4185
- var debug6 = Debug7("mobbdev:checkmarx");
4227
+ var debug7 = Debug8("mobbdev:checkmarx");
4186
4228
  var require2 = createRequire(import.meta.url);
4187
4229
  var getCheckmarxPath = () => {
4188
4230
  const os3 = type();
@@ -4223,14 +4265,14 @@ function validateCheckmarxInstallation() {
4223
4265
  existsSync(getCheckmarxPath());
4224
4266
  }
4225
4267
  async function forkCheckmarx(args, { display }) {
4226
- debug6("fork checkmarx with args %o %s", args.join(" "), display);
4268
+ debug7("fork checkmarx with args %o %s", args.join(" "), display);
4227
4269
  return createSpwan(
4228
4270
  { args, processPath: getCheckmarxPath(), name: "checkmarx" },
4229
4271
  { display }
4230
4272
  );
4231
4273
  }
4232
4274
  async function getCheckmarxReport({ reportPath, repositoryRoot, branch, projectName }, { skipPrompts = false }) {
4233
- debug6("get checkmarx report start %s %s", reportPath, repositoryRoot);
4275
+ debug7("get checkmarx report start %s %s", reportPath, repositoryRoot);
4234
4276
  const { code: loginCode } = await forkCheckmarx(VALIDATE_COMMAND, {
4235
4277
  display: false
4236
4278
  });
@@ -4298,23 +4340,23 @@ async function validateCheckamxCredentials() {
4298
4340
  // src/features/analysis/scanners/snyk.ts
4299
4341
  import { createRequire as createRequire2 } from "node:module";
4300
4342
  import chalk3 from "chalk";
4301
- import Debug8 from "debug";
4343
+ import Debug9 from "debug";
4302
4344
  import { createSpinner as createSpinner3 } from "nanospinner";
4303
4345
  import open from "open";
4304
- var debug7 = Debug8("mobbdev:snyk");
4346
+ var debug8 = Debug9("mobbdev:snyk");
4305
4347
  var require3 = createRequire2(import.meta.url);
4306
4348
  var SNYK_PATH = require3.resolve("snyk/bin/snyk");
4307
4349
  var SNYK_ARTICLE_URL = "https://docs.snyk.io/scan-application-code/snyk-code/getting-started-with-snyk-code/activating-snyk-code-using-the-web-ui/step-1-enabling-the-snyk-code-option";
4308
- debug7("snyk executable path %s", SNYK_PATH);
4350
+ debug8("snyk executable path %s", SNYK_PATH);
4309
4351
  async function forkSnyk(args, { display }) {
4310
- debug7("fork snyk with args %o %s", args, display);
4352
+ debug8("fork snyk with args %o %s", args, display);
4311
4353
  return createFork(
4312
4354
  { args, processPath: SNYK_PATH, name: "checkmarx" },
4313
4355
  { display }
4314
4356
  );
4315
4357
  }
4316
4358
  async function getSnykReport(reportPath, repoRoot, { skipPrompts = false }) {
4317
- debug7("get snyk report start %s %s", reportPath, repoRoot);
4359
+ debug8("get snyk report start %s %s", reportPath, repoRoot);
4318
4360
  const config4 = await forkSnyk(["config"], { display: false });
4319
4361
  const { message: configMessage } = config4;
4320
4362
  if (!configMessage.includes("api: ")) {
@@ -4328,7 +4370,7 @@ async function getSnykReport(reportPath, repoRoot, { skipPrompts = false }) {
4328
4370
  snykLoginSpinner.update({
4329
4371
  text: "\u{1F513} Waiting for Snyk login to complete"
4330
4372
  });
4331
- debug7("no token in the config %s", config4);
4373
+ debug8("no token in the config %s", config4);
4332
4374
  await forkSnyk(["auth"], { display: true });
4333
4375
  snykLoginSpinner.success({ text: "\u{1F513} Login to Snyk Successful" });
4334
4376
  }
@@ -4340,12 +4382,12 @@ async function getSnykReport(reportPath, repoRoot, { skipPrompts = false }) {
4340
4382
  if (scanOutput.includes(
4341
4383
  "Snyk Code is not supported for org: enable in Settings > Snyk Code"
4342
4384
  )) {
4343
- debug7("snyk code is not enabled %s", scanOutput);
4385
+ debug8("snyk code is not enabled %s", scanOutput);
4344
4386
  snykSpinner.error({ text: "\u{1F50D} Snyk configuration needed" });
4345
4387
  const answer = await snykArticlePrompt();
4346
- debug7("answer %s", answer);
4388
+ debug8("answer %s", answer);
4347
4389
  if (answer) {
4348
- debug7("opening the browser");
4390
+ debug8("opening the browser");
4349
4391
  await open(SNYK_ARTICLE_URL);
4350
4392
  }
4351
4393
  console.log(
@@ -4360,18 +4402,18 @@ async function getSnykReport(reportPath, repoRoot, { skipPrompts = false }) {
4360
4402
  }
4361
4403
 
4362
4404
  // src/features/analysis/upload-file.ts
4363
- import Debug9 from "debug";
4405
+ import Debug10 from "debug";
4364
4406
  import fetch2, { File, fileFrom, FormData } from "node-fetch";
4365
- var debug8 = Debug9("mobbdev:upload-file");
4407
+ var debug9 = Debug10("mobbdev:upload-file");
4366
4408
  async function uploadFile({
4367
4409
  file,
4368
4410
  url,
4369
4411
  uploadKey,
4370
4412
  uploadFields
4371
4413
  }) {
4372
- debug8("upload file start %s", url);
4373
- debug8("upload fields %o", uploadFields);
4374
- debug8("upload key %s", uploadKey);
4414
+ debug9("upload file start %s", url);
4415
+ debug9("upload fields %o", uploadFields);
4416
+ debug9("upload key %s", uploadKey);
4375
4417
  const form = new FormData();
4376
4418
  Object.entries(uploadFields).forEach(([key, value]) => {
4377
4419
  form.append(key, value);
@@ -4380,10 +4422,10 @@ async function uploadFile({
4380
4422
  form.append("key", uploadKey);
4381
4423
  }
4382
4424
  if (typeof file === "string") {
4383
- debug8("upload file from path %s", file);
4425
+ debug9("upload file from path %s", file);
4384
4426
  form.append("file", await fileFrom(file));
4385
4427
  } else {
4386
- debug8("upload file from buffer");
4428
+ debug9("upload file from buffer");
4387
4429
  form.append("file", new File([file], "file"));
4388
4430
  }
4389
4431
  const response = await fetch2(url, {
@@ -4391,10 +4433,10 @@ async function uploadFile({
4391
4433
  body: form
4392
4434
  });
4393
4435
  if (!response.ok) {
4394
- debug8("error from S3 %s %s", response.body, response.status);
4436
+ debug9("error from S3 %s %s", response.body, response.status);
4395
4437
  throw new Error(`Failed to upload the file: ${response.status}`);
4396
4438
  }
4397
- debug8("upload file done");
4439
+ debug9("upload file done");
4398
4440
  }
4399
4441
 
4400
4442
  // src/features/analysis/index.ts
@@ -4409,9 +4451,9 @@ async function downloadRepo({
4409
4451
  }) {
4410
4452
  const { createSpinner: createSpinner4 } = Spinner2({ ci });
4411
4453
  const repoSpinner = createSpinner4("\u{1F4BE} Downloading Repo").start();
4412
- debug9("download repo %s %s %s", repoUrl, dirname);
4454
+ debug10("download repo %s %s %s", repoUrl, dirname);
4413
4455
  const zipFilePath = path6.join(dirname, "repo.zip");
4414
- debug9("download URL: %s auth headers: %o", downloadUrl, authHeaders);
4456
+ debug10("download URL: %s auth headers: %o", downloadUrl, authHeaders);
4415
4457
  const response = await fetch3(downloadUrl, {
4416
4458
  method: "GET",
4417
4459
  headers: {
@@ -4419,7 +4461,7 @@ async function downloadRepo({
4419
4461
  }
4420
4462
  });
4421
4463
  if (!response.ok) {
4422
- debug9("SCM zipball request failed %s %s", response.body, response.status);
4464
+ debug10("SCM zipball request failed %s %s", response.body, response.status);
4423
4465
  repoSpinner.error({ text: "\u{1F4BE} Repo download failed" });
4424
4466
  throw new Error(`Can't access ${chalk4.bold(repoUrl)}`);
4425
4467
  }
@@ -4433,7 +4475,7 @@ async function downloadRepo({
4433
4475
  if (!repoRoot) {
4434
4476
  throw new Error("Repo root not found");
4435
4477
  }
4436
- debug9("repo root %s", repoRoot);
4478
+ debug10("repo root %s", repoRoot);
4437
4479
  repoSpinner.success({ text: "\u{1F4BE} Repo downloaded successfully" });
4438
4480
  return path6.join(dirname, repoRoot);
4439
4481
  }
@@ -4450,7 +4492,7 @@ var getReportUrl = ({
4450
4492
  projectId,
4451
4493
  fixReportId
4452
4494
  }) => `${WEB_APP_URL}/organization/${organizationId}/project/${projectId}/report/${fixReportId}`;
4453
- var debug9 = Debug10("mobbdev:index");
4495
+ var debug10 = Debug11("mobbdev:index");
4454
4496
  var packageJson = JSON.parse(
4455
4497
  fs3.readFileSync(path6.join(getDirName2(), "../package.json"), "utf8")
4456
4498
  );
@@ -4460,7 +4502,7 @@ if (!semver.satisfies(process.version, packageJson.engines.node)) {
4460
4502
  );
4461
4503
  }
4462
4504
  var config2 = new Configstore(packageJson.name, { apiToken: "" });
4463
- debug9("config %o", config2);
4505
+ debug10("config %o", config2);
4464
4506
  async function runAnalysis(params, options) {
4465
4507
  try {
4466
4508
  await _scan(
@@ -4516,7 +4558,7 @@ async function _scan(params, { skipPrompts = false } = {}) {
4516
4558
  githubToken: githubActionToken,
4517
4559
  command
4518
4560
  } = params;
4519
- debug9("start %s %s", dirname, repo);
4561
+ debug10("start %s %s", dirname, repo);
4520
4562
  const { createSpinner: createSpinner4 } = Spinner2({ ci });
4521
4563
  skipPrompts = skipPrompts || ci;
4522
4564
  let gqlClient = new GQLClient({
@@ -4581,9 +4623,9 @@ async function _scan(params, { skipPrompts = false } = {}) {
4581
4623
  });
4582
4624
  const reference = ref ?? await scm.getRepoDefaultBranch();
4583
4625
  const { sha } = await scm.getReferenceData(reference);
4584
- debug9("org id %s", organizationId);
4585
- debug9("project id %s", projectId);
4586
- debug9("default branch %s", reference);
4626
+ debug10("org id %s", organizationId);
4627
+ debug10("project id %s", projectId);
4628
+ debug10("default branch %s", reference);
4587
4629
  const repositoryRoot = await downloadRepo({
4588
4630
  repoUrl: repo,
4589
4631
  dirname,
@@ -4611,44 +4653,39 @@ async function _scan(params, { skipPrompts = false } = {}) {
4611
4653
  }
4612
4654
  uploadReportSpinner.success({ text: "\u{1F4C1} Report uploaded successfully" });
4613
4655
  const mobbSpinner = createSpinner4("\u{1F575}\uFE0F\u200D\u2642\uFE0F Initiating Mobb analysis").start();
4614
- const sendReportRes = await sendReport();
4656
+ const sendReportRes = await sendReport({
4657
+ gqlClient,
4658
+ spinner: mobbSpinner,
4659
+ submitVulnerabilityReportVariables: {
4660
+ fixReportId: reportUploadInfo.fixReportId,
4661
+ repoUrl: z11.string().parse(repo),
4662
+ reference,
4663
+ projectId,
4664
+ vulnerabilityReportFileName: "report.json",
4665
+ sha,
4666
+ experimentalEnabled,
4667
+ pullRequest: params.pullRequest
4668
+ }
4669
+ });
4615
4670
  if (command === "review") {
4616
- await gqlClient.subscribeToAnalysis(
4617
- { analysisId: sendReportRes.submitVulnerabilityReport.fixReportId },
4618
- (analysisId) => handleFinishedAnalysis({
4671
+ await gqlClient.subscribeToAnalysis({
4672
+ subscribeToAnalysisParams: {
4673
+ analysisId: sendReportRes.submitVulnerabilityReport.fixReportId
4674
+ },
4675
+ callback: (analysisId) => handleFinishedAnalysis({
4619
4676
  analysisId,
4620
4677
  gqlClient,
4621
4678
  scm,
4622
4679
  githubActionToken: z11.string().parse(githubActionToken),
4623
4680
  scanner: z11.nativeEnum(SCANNERS).parse(scanner)
4624
- })
4625
- );
4681
+ }),
4682
+ callbackStates: ["Finished"]
4683
+ });
4626
4684
  }
4627
4685
  mobbSpinner.success({
4628
4686
  text: "\u{1F575}\uFE0F\u200D\u2642\uFE0F Generating fixes..."
4629
4687
  });
4630
4688
  await askToOpenAnalysis();
4631
- async function sendReport() {
4632
- try {
4633
- const sumbitRes = await gqlClient.submitVulnerabilityReport({
4634
- fixReportId: reportUploadInfo.fixReportId,
4635
- repoUrl: z11.string().parse(repo),
4636
- reference,
4637
- projectId,
4638
- vulnerabilityReportFileName: "report.json",
4639
- sha,
4640
- experimentalEnabled,
4641
- pullRequest: params.pullRequest
4642
- });
4643
- if (sumbitRes.submitVulnerabilityReport.__typename !== "VulnerabilityReport") {
4644
- throw new Error("\u{1F575}\uFE0F\u200D\u2642\uFE0F Mobb analysis failed");
4645
- }
4646
- return sumbitRes;
4647
- } catch (e) {
4648
- mobbSpinner.error({ text: "\u{1F575}\uFE0F\u200D\u2642\uFE0F Mobb analysis failed" });
4649
- throw e;
4650
- }
4651
- }
4652
4689
  async function getReport(scanner2) {
4653
4690
  const reportPath2 = path6.join(dirname, "report.json");
4654
4691
  switch (scanner2) {
@@ -4724,9 +4761,9 @@ async function _scan(params, { skipPrompts = false } = {}) {
4724
4761
  });
4725
4762
  loginSpinner.spin();
4726
4763
  if (encryptedApiToken) {
4727
- debug9("encrypted API token received %s", encryptedApiToken);
4764
+ debug10("encrypted API token received %s", encryptedApiToken);
4728
4765
  newApiToken = crypto.privateDecrypt(privateKey, Buffer.from(encryptedApiToken, "base64")).toString("utf-8");
4729
- debug9("API token decrypted");
4766
+ debug10("API token decrypted");
4730
4767
  break;
4731
4768
  }
4732
4769
  await sleep(LOGIN_CHECK_DELAY);
@@ -4739,7 +4776,7 @@ async function _scan(params, { skipPrompts = false } = {}) {
4739
4776
  }
4740
4777
  gqlClient = new GQLClient({ apiKey: newApiToken });
4741
4778
  if (await gqlClient.verifyToken()) {
4742
- debug9("set api token %s", newApiToken);
4779
+ debug10("set api token %s", newApiToken);
4743
4780
  config2.set("apiToken", newApiToken);
4744
4781
  loginSpinner.success({ text: "\u{1F513} Login to Mobb successful!" });
4745
4782
  } else {
@@ -4802,7 +4839,9 @@ async function _scan(params, { skipPrompts = false } = {}) {
4802
4839
  uploadReportSpinner2.success({
4803
4840
  text: "\u{1F4C1} Uploading Report successful!"
4804
4841
  });
4805
- const digestSpinner = createSpinner4("\u{1F575}\uFE0F\u200D\u2642\uFE0F Digesting report").start();
4842
+ const digestSpinner = createSpinner4(
4843
+ progressMassages.processingVulnerabilityReport
4844
+ ).start();
4806
4845
  let vulnFiles = [];
4807
4846
  const gitInfo = await getGitInfo(srcPath);
4808
4847
  try {
@@ -4810,12 +4849,19 @@ async function _scan(params, { skipPrompts = false } = {}) {
4810
4849
  fixReportId: reportUploadInfo.fixReportId,
4811
4850
  projectId
4812
4851
  });
4813
- const finalState = await gqlClient.waitFixReportInit(
4814
- reportUploadInfo.fixReportId,
4815
- true
4816
- );
4817
- if (finalState !== "Digested") {
4818
- throw new Error("Digesting report failed");
4852
+ try {
4853
+ await gqlClient.subscribeToAnalysis({
4854
+ subscribeToAnalysisParams: {
4855
+ analysisId: reportUploadInfo.fixReportId
4856
+ },
4857
+ callback: () => digestSpinner.update({
4858
+ text: progressMassages.processingVulnerabilityReportSuccess
4859
+ }),
4860
+ callbackStates: ["Digested", "Finished"],
4861
+ timeoutInMs: VUL_REPORT_DIGEST_TIMEOUT_MS
4862
+ });
4863
+ } catch (e) {
4864
+ throw new Error(progressMassages.processingVulnerabilityReportFailed);
4819
4865
  }
4820
4866
  vulnFiles = await gqlClient.getVulnerabilityReportPaths(
4821
4867
  vulnerabilityReportId
@@ -4825,7 +4871,7 @@ async function _scan(params, { skipPrompts = false } = {}) {
4825
4871
  throw e;
4826
4872
  }
4827
4873
  digestSpinner.success({
4828
- text: "\u{1F575}\uFE0F\u200D\u2642\uFE0F Digesting report successful!"
4874
+ text: progressMassages.processingVulnerabilityReportSuccess
4829
4875
  });
4830
4876
  const zippingSpinner = createSpinner4("\u{1F4E6} Zipping repo").start();
4831
4877
  const zipBuffer = await pack(srcPath, vulnFiles);
@@ -4845,12 +4891,16 @@ async function _scan(params, { skipPrompts = false } = {}) {
4845
4891
  uploadRepoSpinner.success({ text: "\u{1F4C1} Uploading Repo successful!" });
4846
4892
  const mobbSpinner2 = createSpinner4("\u{1F575}\uFE0F\u200D\u2642\uFE0F Initiating Mobb analysis").start();
4847
4893
  try {
4848
- await gqlClient.submitVulnerabilityReport({
4849
- fixReportId: reportUploadInfo.fixReportId,
4850
- projectId,
4851
- repoUrl: repo || gitInfo.repoUrl || getTopLevelDirName(srcPath),
4852
- reference: gitInfo.reference || "no-branch",
4853
- sha: commitHash || gitInfo.hash || "0123456789abcdef"
4894
+ await sendReport({
4895
+ gqlClient,
4896
+ spinner: mobbSpinner2,
4897
+ submitVulnerabilityReportVariables: {
4898
+ fixReportId: reportUploadInfo.fixReportId,
4899
+ projectId,
4900
+ repoUrl: repo || gitInfo.repoUrl || getTopLevelDirName(srcPath),
4901
+ reference: gitInfo.reference || "no-branch",
4902
+ sha: commitHash || gitInfo.hash || "0123456789abcdef"
4903
+ }
4854
4904
  });
4855
4905
  } catch (e) {
4856
4906
  mobbSpinner2.error({ text: "\u{1F575}\uFE0F\u200D\u2642\uFE0F Mobb analysis failed" });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "mobbdev",
3
- "version": "0.0.92",
3
+ "version": "0.0.93",
4
4
  "description": "Automated secure code remediation tool",
5
5
  "repository": "https://github.com/mobb-dev/bugsy",
6
6
  "main": "dist/index.js",