Skip to content

Commit

Permalink
CM-42037 - Add AI remediations for IaC and SAST (#81)
Browse files Browse the repository at this point in the history
  • Loading branch information
MarshalX authored Dec 11, 2024
1 parent a4d7848 commit f5f8c6f
Show file tree
Hide file tree
Showing 38 changed files with 383 additions and 368 deletions.
9 changes: 8 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,11 @@

## [Unreleased]

## [2.2.0] - 2024-12-11

- Add AI remediations for IaC and SAST
- Fix "Path to executable" field applying in the settings

## [2.1.0] - 2024-10-07

- Add sync flow for Secrets and IaC
Expand Down Expand Up @@ -125,6 +130,8 @@

The first public release of the plugin.

[2.2.0]: https://github.com/cycodehq/intellij-platform-plugin/releases/tag/v2.2.0

[2.1.0]: https://github.com/cycodehq/intellij-platform-plugin/releases/tag/v2.1.0

[2.0.1]: https://github.com/cycodehq/intellij-platform-plugin/releases/tag/v2.0.1
Expand Down Expand Up @@ -175,4 +182,4 @@ The first public release of the plugin.

[1.0.0]: https://github.com/cycodehq/intellij-platform-plugin/releases/tag/v1.0.0

[Unreleased]: https://github.com/cycodehq/intellij-platform-plugin/compare/v2.1.0...HEAD
[Unreleased]: https://github.com/cycodehq/intellij-platform-plugin/compare/v2.2.0...HEAD
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ pluginGroup = com.cycode.plugin
pluginName = Cycode
pluginRepositoryUrl = https://github.com/cycodehq/intellij-platform-plugin
# SemVer format -> https://semver.org
pluginVersion = 2.1.0
pluginVersion = 2.2.0

# Supported build number ranges and IntelliJ Platform versions -> https://plugins.jetbrains.com/docs/intellij/build-number-ranges.html
pluginSinceBuild = 231
Expand Down
2 changes: 1 addition & 1 deletion src/main/kotlin/com/cycode/plugin/Consts.kt
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ class Consts {
companion object {
val PLUGIN_PATH = PathManager.getPluginsPath() + "/cycode-intellij-platform-plugin"
val DEFAULT_CLI_PATH = getDefaultCliPath()
const val REQUIRED_CLI_VERSION = "1.11.0"
const val REQUIRED_CLI_VERSION = "2.1.0"

const val CYCODE_DOMAIN = "cycode.com"

Expand Down
4 changes: 2 additions & 2 deletions src/main/kotlin/com/cycode/plugin/cli/CliWrapper.kt
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ class CliOSProcessHandler(commandLine: GeneralCommandLine) : OSProcessHandler(co
}


class CliWrapper(val executablePath: String, val workDirectory: String? = null) {
class CliWrapper(val workDirectory: String? = null) {
val pluginSettings = pluginSettings()

var mapper: ObjectMapper = jacksonObjectMapper()
Expand All @@ -42,7 +42,7 @@ class CliWrapper(val executablePath: String, val workDirectory: String? = null)
): CliResult<T> {
val commandLine = GeneralCommandLine()
commandLine.charset = Charset.forName("UTF-8")
commandLine.exePath = executablePath
commandLine.exePath = pluginSettings.cliPath

if (workDirectory != null) {
commandLine.workDirectory = File(workDirectory)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package com.cycode.plugin.cli.models

data class AiRemediationResult(
val result: Boolean,
val message: String,
val data: AiRemediationResultData? = null,
)

data class AiRemediationResultData(
val remediation: String,
val isFixAvailable: Boolean,
)
12 changes: 0 additions & 12 deletions src/main/kotlin/com/cycode/plugin/cli/models/AuthCheckResult.kt

This file was deleted.

19 changes: 19 additions & 0 deletions src/main/kotlin/com/cycode/plugin/cli/models/StatusResult.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package com.cycode.plugin.cli.models

data class SupportedModulesStatus(
// TODO(MarshalX): respect enabled/disabled scanning modules
val secretScanning: Boolean,
val scaScanning: Boolean,
val iacScanning: Boolean,
val sastScanning: Boolean,
val aiLargeLanguageModel: Boolean,
)

data class StatusResult(
val program: String,
val version: String,
val isAuthenticated: Boolean,
val userId: String?,
val tenantId: String?,
val supportedModules: SupportedModulesStatus,
)
6 changes: 0 additions & 6 deletions src/main/kotlin/com/cycode/plugin/cli/models/VersionResult.kt

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.cycode.plugin.cli.models.scanResult

interface DetectionBase {
val id: String
val severity: String
val detectionDetails: ScanDetectionDetailsBase

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@ import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.models.scanResult.DetectionBase

data class IacDetection(
val message: String,
override val detectionDetails: IacDetectionDetails,
override val id: String,
override val severity: String,
override val detectionDetails: IacDetectionDetails,
val message: String,
val type: String,
val detectionRuleId: String, // UUID
val detectionTypeId: String, // UUID
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@ import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.models.scanResult.DetectionBase

data class SastDetection(
val message: String,
override val detectionDetails: SastDetectionDetails,
override val id: String,
override val severity: String,
override val detectionDetails: SastDetectionDetails,
val message: String,
val type: String,
val detectionRuleId: String, // UUID
val detectionTypeId: String, // UUID
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,10 @@ import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.models.scanResult.DetectionBase

data class ScaDetection(
val message: String,
override val detectionDetails: ScaDetectionDetails,
override val id: String,
override val severity: String,
override val detectionDetails: ScaDetectionDetails,
val message: String,
val type: String,
val detectionRuleId: String,
val detectionTypeId: String,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,10 @@ import com.cycode.plugin.cli.models.scanResult.DetectionBase
const val IDE_ENTRY_LINE_NUMBER = 1

data class SecretDetection(
val message: String,
override val detectionDetails: SecretDetectionDetails,
override val id: String,
override val severity: String,
override val detectionDetails: SecretDetectionDetails,
val message: String,
val type: String,
val detectionRuleId: String, // UUID
val detectionTypeId: String, // UUID
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,27 +18,20 @@ class AuthContentTab : Component<CycodeService>() {
return BorderedPanel().apply {
add(JPanel().apply {
layout = GridBagLayout()
add(add(JPanel().apply {
add(createClickableLabel(CycodeBundle.message("cliReqInfoLabel")))
}), GridBagConstraints().apply {
gridy = 0
insets = JBUI.insetsBottom(10)
anchor = GridBagConstraints.NORTHWEST
})
add(JButton(CycodeBundle.message("authBtn")).apply {
addActionListener {
this.setEnabled(false)
service.startAuth()
}
}, GridBagConstraints().apply {
gridy = 1
gridy = 0
insets = JBUI.insetsBottom(10)
fill = GridBagConstraints.HORIZONTAL
})
add(add(JPanel().apply {
add(createClickableLabel(CycodeBundle.message("howToUseLabel")))
}), GridBagConstraints().apply {
gridy = 2
gridy = 1
anchor = GridBagConstraints.NORTHWEST
})
}, BorderLayout.NORTH)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.cycode.plugin.components.toolWindow.components.cycodeActionToolBar.actions

import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.CliScanType
import com.cycode.plugin.services.cycode
import com.cycode.plugin.services.pluginState
import com.intellij.icons.AllIcons
Expand All @@ -27,10 +28,10 @@ class RunAllAction :
val project = e.project ?: return
val service = cycode(project)

service.startSecretScanForCurrentProject()
service.startScaScanForCurrentProject()
service.startIacScanForCurrentProject()
service.startSastScanForCurrentProject()
service.startScanForCurrentProject(CliScanType.Secret)
service.startScanForCurrentProject(CliScanType.Sca)
service.startScanForCurrentProject(CliScanType.Iac)
service.startScanForCurrentProject(CliScanType.Sast)
}

override fun update(e: AnActionEvent) {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.cycode.plugin.components.toolWindow.components.scanContentTab

import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.CliScanType
import com.cycode.plugin.components.Component
import com.cycode.plugin.components.common.createClickableLabel
import com.cycode.plugin.services.CycodeService
Expand Down Expand Up @@ -29,22 +30,22 @@ class ScanContentTab : Component<CycodeService>() {
addComponentToPanel(createClickableLabel(CycodeBundle.message("scanTabTitleLabel")))
addComponentToPanel(
JButton(CycodeBundle.message("scanTabSecretsBtn")).apply {
addActionListener { service.startSecretScanForCurrentProject() }
addActionListener { service.startScanForCurrentProject(CliScanType.Secret) }
},
)
addComponentToPanel(
JButton(CycodeBundle.message("scanTabScaBtn")).apply {
addActionListener { service.startScaScanForCurrentProject() }
addActionListener { service.startScanForCurrentProject(CliScanType.Sca) }
},
)
addComponentToPanel(
JButton(CycodeBundle.message("scanTabIacBtn")).apply {
addActionListener { service.startIacScanForCurrentProject() }
addActionListener { service.startScanForCurrentProject(CliScanType.Iac) }
},
)
addComponentToPanel(
JButton(CycodeBundle.message("scanTabSastBtn")).apply {
addActionListener { service.startSastScanForCurrentProject() }
addActionListener { service.startScanForCurrentProject(CliScanType.Sast) }
},
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -123,8 +123,8 @@ class TreeView(
val card = when (detection) {
is SecretDetection -> SecretViolationCardContentTab(project).getContent(detection)
is ScaDetection -> ScaViolationCardContentTab().getContent(detection)
is IacDetection -> IacViolationCardContentTab().getContent(detection)
is SastDetection -> SastViolationCardContentTab().getContent(detection)
is IacDetection -> IacViolationCardContentTab(project).getContent(detection)
is SastDetection -> SastViolationCardContentTab(project).getContent(detection)
else -> return
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package com.cycode.plugin.components.toolWindow.components.treeView.components.detectionNodeContextMenu

import com.cycode.plugin.CycodeBundle
import com.cycode.plugin.cli.CliScanType
import com.cycode.plugin.components.toolWindow.components.treeView.TreeView
import com.cycode.plugin.components.toolWindow.components.treeView.nodes.*
import com.cycode.plugin.components.toolWindow.components.treeView.openDetectionInFile
Expand Down Expand Up @@ -69,33 +70,33 @@ class DetectionNodeContextMenu(

// FIXME(MarshalX): add some key field instead of abusing name?
when (node.name) {
CycodeBundle.message("secretDisplayName") -> service.startSecretScanForCurrentProject()
CycodeBundle.message("scaDisplayName") -> service.startScaScanForCurrentProject()
CycodeBundle.message("iacDisplayName") -> service.startIacScanForCurrentProject()
CycodeBundle.message("sastDisplayName") -> service.startSastScanForCurrentProject()
CycodeBundle.message("secretDisplayName") -> service.startScanForCurrentProject(CliScanType.Secret)
CycodeBundle.message("scaDisplayName") -> service.startScanForCurrentProject(CliScanType.Sca)
CycodeBundle.message("iacDisplayName") -> service.startScanForCurrentProject(CliScanType.Iac)
CycodeBundle.message("sastDisplayName") -> service.startScanForCurrentProject(CliScanType.Sast)
}
}

private fun onRescanOptionClicked() {
when (val node = getUnknownNode()) {
is SecretDetectionNode -> service.startPathSecretScan(
node.detection.detectionDetails.getFilepath(),
onDemand = true
is SecretDetectionNode -> service.startScan(
CliScanType.Secret,
listOf(node.detection.detectionDetails.getFilepath()),
)

is ScaDetectionNode -> service.startPathScaScan(
node.detection.detectionDetails.getFilepath(),
onDemand = true
is ScaDetectionNode -> service.startScan(
CliScanType.Sca,
listOf(node.detection.detectionDetails.getFilepath()),
)

is IacDetectionNode -> service.startPathIacScan(
node.detection.detectionDetails.getFilepath(),
onDemand = true
is IacDetectionNode -> service.startScan(
CliScanType.Iac,
listOf(node.detection.detectionDetails.getFilepath()),
)

is SastDetectionNode -> service.startPathSastScan(
node.detection.detectionDetails.getFilepath(),
onDemand = true
is SastDetectionNode -> service.startScan(
CliScanType.Sast,
listOf(node.detection.detectionDetails.getFilepath()),
)
}
}
Expand Down
Loading

0 comments on commit f5f8c6f

Please sign in to comment.