Skip to content

Commit dcc29e2

Browse files
committed
Merge branch 'main' into nate/fix-tests
2 parents 857f01e + 5031046 commit dcc29e2

34 files changed

Lines changed: 883 additions & 84 deletions

build.js

Lines changed: 29 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -1,70 +1,70 @@
11
#!/usr/bin/env node
22

3-
const { execSync } = require('child_process');
4-
const fs = require('fs');
5-
const path = require('path');
6-
const os = require('os');
3+
const { execSync } = require("child_process");
4+
const fs = require("fs");
5+
const path = require("path");
6+
const os = require("os");
77

88
// Define target platforms and architectures
99
const targets = [
10-
{ platform: 'darwin', arch: 'amd64', goarch: 'amd64' },
11-
{ platform: 'darwin', arch: 'arm64', goarch: 'arm64' },
12-
{ platform: 'linux', arch: 'x64', goarch: 'amd64' },
13-
{ platform: 'linux', arch: 'arm64', goarch: 'arm64' },
14-
{ platform: 'win32', arch: 'x64', goarch: 'amd64' }
10+
{ platform: "darwin", arch: "amd64", goarch: "amd64" },
11+
{ platform: "darwin", arch: "arm64", goarch: "arm64" },
12+
{ platform: "linux", arch: "x64", goarch: "amd64" },
13+
{ platform: "linux", arch: "arm64", goarch: "arm64" },
14+
{ platform: "win32", arch: "x64", goarch: "amd64" },
1515
];
1616

1717
// Get package version from package.json
18-
const packageJson = JSON.parse(fs.readFileSync('package.json', 'utf8'));
18+
const packageJson = JSON.parse(fs.readFileSync("package.json", "utf8"));
1919
const version = packageJson.version;
2020

2121
// Create bin directory if it doesn't exist
22-
if (!fs.existsSync('bin')) {
23-
fs.mkdirSync('bin');
22+
if (!fs.existsSync("bin")) {
23+
fs.mkdirSync("bin");
2424
}
2525

2626
// Build for each target
2727
for (const target of targets) {
2828
const { platform, arch, goarch } = target;
29-
29+
3030
// Set binary name based on platform
31-
const binaryName = platform === 'win32' ? 'rules-cli.exe' : 'rules-cli';
32-
31+
const binaryName = platform === "win32" ? "rules-cli.exe" : "rules-cli";
32+
3333
// Create output directory
34-
const outputDir = path.join('bin', `${platform}-${arch}`);
34+
const outputDir = path.join("bin", `${platform}-${arch}`);
3535
if (!fs.existsSync(outputDir)) {
3636
fs.mkdirSync(outputDir, { recursive: true });
3737
}
38-
38+
3939
const outputPath = path.join(outputDir, binaryName);
40-
40+
4141
// Set environment variables for cross-compilation
4242
const env = {
4343
...process.env,
44-
GOOS: platform === 'win32' ? 'windows' : platform,
44+
GOOS: platform === "win32" ? "windows" : platform,
4545
GOARCH: goarch,
46-
CGO_ENABLED: '0'
46+
CGO_ENABLED: "0",
4747
};
48-
48+
4949
console.log(`Building for ${platform}-${arch}...`);
50-
50+
5151
try {
5252
// Build the binary with version info
5353
execSync(
54-
`go build -ldflags="-s -w -X main.Version=${version}" -o ${outputPath}`,
55-
{ env, stdio: 'inherit' }
54+
`go build -ldflags="-s -w -X main.Version=${version} -X rules-cli/internal/utils.Version=${version}" -o ${outputPath}`,
55+
{ env, stdio: "inherit" }
5656
);
57-
57+
5858
console.log(`Built ${outputPath}`);
59-
59+
6060
// Make binary executable (not needed for Windows)
61-
if (platform !== 'win32') {
62-
fs.chmodSync(outputPath, '755');
61+
if (platform !== "win32") {
62+
fs.chmodSync(outputPath, "755");
6363
}
6464
} catch (error) {
6565
console.error(`Failed to build for ${platform}-${arch}: ${error.message}`);
6666
process.exit(1);
6767
}
6868
}
6969

70-
console.log('Build completed successfully!');
70+
console.log("Build completed successfully!");

cmd/add.go

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
"rules-cli/internal/registry"
1111
"rules-cli/internal/ruleset"
1212

13+
"github.com/fatih/color"
1314
"github.com/spf13/cobra"
1415
)
1516

@@ -91,7 +92,7 @@ func loadOrCreateRuleSet(rulesJSONPath string) (*ruleset.RuleSet, error) {
9192

9293
// Create a default ruleset
9394
rs := ruleset.DefaultRuleSet(filepath.Base(filepath.Dir(rulesJSONPath)))
94-
fmt.Println("Creating new rules.json file with default structure")
95+
color.Cyan("Creating new rules.json file with default structure")
9596
return rs, nil
9697
} else if err != nil {
9798
return nil, fmt.Errorf("failed to check rules.json file: %w", err)
@@ -109,9 +110,9 @@ func loadOrCreateRuleSet(rulesJSONPath string) (*ruleset.RuleSet, error) {
109110
// downloadRule downloads a rule from the registry
110111
func downloadRule(client *registry.Client, ruleName, ruleVersion, rulesDir string) error {
111112
if strings.HasPrefix(ruleName, "gh:") {
112-
fmt.Printf("Downloading rules from GitHub repository '%s' (src/ directory)...\n", ruleName[3:])
113+
color.Cyan("Downloading rules from GitHub repository '%s' (src/ directory)...", ruleName[3:])
113114
} else {
114-
fmt.Printf("Downloading rule '%s' (version %s) from registry API...\n", ruleName, ruleVersion)
115+
color.Cyan("Downloading rule '%s' (version %s) from registry API...", ruleName, ruleVersion)
115116
}
116117

117118
return client.DownloadRule(ruleName, ruleVersion, rulesDir)
@@ -157,7 +158,7 @@ func runAddCommand(cmd *cobra.Command, args []string) error {
157158
return fmt.Errorf("failed to save ruleset: %w", err)
158159
}
159160

160-
fmt.Printf("Rule '%s' (version %s) added successfully\n", ruleName, ruleVersion)
161+
color.Green("Rule '%s' (version %s) added successfully", ruleName, ruleVersion)
161162

162163
// Print format suggestion at the very end if applicable
163164
if formatSuggestion != "" {

cmd/create.go

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,11 @@ import (
66
"os"
77
"strings"
88

9+
"rules-cli/internal/ruleset"
10+
11+
"github.com/fatih/color"
912
"github.com/manifoldco/promptui"
1013
"github.com/spf13/cobra"
11-
"rules-cli/internal/ruleset"
1214
)
1315

1416
var (
@@ -81,7 +83,7 @@ This command does not modify the rules.json file.`,
8183
if len(args) > 1 {
8284
rule.Body = args[1]
8385
} else {
84-
fmt.Println("Enter rule body (press Ctrl+D on a new line when done):")
86+
color.Cyan("Enter rule body (press Ctrl+D on a new line when done):")
8587
scanner := bufio.NewScanner(os.Stdin)
8688
var bodyLines []string
8789
for scanner.Scan() {
@@ -98,7 +100,7 @@ This command does not modify the rules.json file.`,
98100
return fmt.Errorf("failed to create rule: %w", err)
99101
}
100102

101-
fmt.Printf("Rule '%s' created successfully\n", ruleName)
103+
color.Green("Rule '%s' created successfully", ruleName)
102104
return nil
103105
},
104106
}

cmd/init.go

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77

88
"rules-cli/internal/formats"
99

10+
"github.com/fatih/color"
1011
"github.com/spf13/cobra"
1112
)
1213

@@ -18,7 +19,7 @@ var initCmd = &cobra.Command{
1819
This creates the necessary directory structure and an empty rules.json file.`,
1920
Example: ` rules init`,
2021
RunE: func(cmd *cobra.Command, args []string) error {
21-
fmt.Printf("Initializing rules with format: %s\n", format)
22+
color.Cyan("Initializing rules with format: %s", format)
2223

2324
// Check if rules.json doesn't exist
2425
rulesJSONPath, err := formats.GetRulesJSONPath(format)
@@ -31,16 +32,16 @@ This creates the necessary directory structure and an empty rules.json file.`,
3132
formatFolders, err := formats.FindRulesFormats()
3233
if err == nil && len(formatFolders) > 0 {
3334
// Suggest rendering to the user
34-
fmt.Printf("Found existing rules folder(s): %s\n", strings.Join(formatFolders, ", "))
35-
fmt.Printf("Consider running 'rules render %s' to initialize rules.json from existing rules\n", formatFolders[0])
35+
color.Yellow("Found existing rules folder(s): %s", strings.Join(formatFolders, ", "))
36+
color.Yellow("Consider running 'rules render %s' to initialize rules.json from existing rules", formatFolders[0])
3637
}
3738
}
3839

3940
if err := formats.InitializeFormat(format); err != nil {
4041
return fmt.Errorf("initialization failed: %w", err)
4142
}
4243

43-
fmt.Printf("Rules initialized successfully. Format: %s\n", format)
44+
color.Green("Rules initialized successfully. Format: %s", format)
4445
return nil
4546
},
4647
}

cmd/install.go

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
"rules-cli/internal/registry"
1111
"rules-cli/internal/ruleset"
1212

13+
"github.com/fatih/color"
1314
"github.com/spf13/cobra"
1415
)
1516

@@ -62,7 +63,7 @@ This ensures the rules directory matches exactly what's defined in rules.json.`,
6263

6364
// Create a default ruleset
6465
rs = ruleset.DefaultRuleSet(filepath.Base(filepath.Dir(rulesJSONPath)))
65-
fmt.Println("Creating new rules.json file with default structure")
66+
color.Cyan("Creating new rules.json file with default structure")
6667

6768
// Save the new ruleset
6869
if err := rs.SaveRuleSet(rulesJSONPath); err != nil {
@@ -82,20 +83,20 @@ This ensures the rules directory matches exactly what's defined in rules.json.`,
8283
if _, err := os.Stat(rulesDir); err == nil {
8384
// Directory exists, check if we should clean it
8485
if !forceInstall {
85-
fmt.Printf("This will remove all existing rules in '%s' and reinstall them from rules.json.\n", rulesDir)
86+
color.Yellow("This will remove all existing rules in '%s' and reinstall them from rules.json.", rulesDir)
8687
fmt.Print("Continue? (y/N): ")
8788

8889
var response string
8990
fmt.Scanln(&response)
9091

9192
if strings.ToLower(response) != "y" {
92-
fmt.Println("Installation cancelled.")
93+
color.Yellow("Installation cancelled.")
9394
return nil
9495
}
9596
}
9697

9798
// Remove all files and directories in the rules directory
98-
fmt.Printf("Removing existing rules from '%s'...\n", rulesDir)
99+
color.Cyan("Removing existing rules from '%s'...", rulesDir)
99100
if err := removeContents(rulesDir); err != nil {
100101
return fmt.Errorf("failed to clean rules directory: %w", err)
101102
}
@@ -112,9 +113,9 @@ This ensures the rules directory matches exactly what's defined in rules.json.`,
112113
client := registry.NewClient(cfg.RegistryURL)
113114

114115
// Install each rule from rules.json
115-
fmt.Println("Installing rules from rules.json...")
116+
color.Cyan("Installing rules from rules.json...")
116117
if len(rs.Rules) == 0 {
117-
fmt.Println("No rules found in rules.json.")
118+
color.Yellow("No rules found in rules.json.")
118119

119120
// Print format suggestion at the very end if applicable
120121
if formatSuggestion != "" {
@@ -128,18 +129,18 @@ This ensures the rules directory matches exactly what's defined in rules.json.`,
128129
errorCount := 0
129130

130131
for ruleName, ruleVersion := range rs.Rules {
131-
fmt.Printf("Installing rule '%s' (version: %s)...\n", ruleName, ruleVersion)
132+
color.Cyan("Installing rule '%s' (version: %s)...", ruleName, ruleVersion)
132133

133134
if err := client.DownloadRule(ruleName, ruleVersion, rulesDir); err != nil {
134-
fmt.Printf("Error installing rule '%s': %v\n", ruleName, err)
135+
color.Red("Error installing rule '%s': %v", ruleName, err)
135136
errorCount++
136137
} else {
137138
successCount++
138139
}
139140
}
140141

141142
// Print summary
142-
fmt.Printf("\nInstallation complete: %d rules installed, %d failed\n", successCount, errorCount)
143+
color.Green("\nInstallation complete: %d rules installed, %d failed", successCount, errorCount)
143144

144145
// Print format suggestion at the very end if applicable
145146
if formatSuggestion != "" {

cmd/login.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,10 @@ package cmd
33
import (
44
"fmt"
55

6+
"rules-cli/internal/auth"
7+
68
"github.com/fatih/color"
79
"github.com/spf13/cobra"
8-
"rules-cli/internal/auth"
910
)
1011

1112
// loginCmd represents the login command
@@ -17,7 +18,7 @@ var loginCmd = &cobra.Command{
1718
fmt.Println("Starting login process...")
1819

1920
// Call the login function from the auth package
20-
authConfig, err := auth.Login(false)
21+
authConfig, err := auth.Login()
2122
if err != nil {
2223
color.Red("Login failed: %v", err)
2324
return

cmd/logout.go

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
package cmd
22

33
import (
4-
"github.com/spf13/cobra"
54
"rules-cli/internal/auth"
5+
6+
"github.com/fatih/color"
7+
"github.com/spf13/cobra"
68
)
79

810
// logoutCmd represents the logout command
@@ -11,6 +13,7 @@ var logoutCmd = &cobra.Command{
1113
Short: "Log out from the registry service",
1214
Long: `Logs the user out by removing stored authentication information.`,
1315
Run: func(cmd *cobra.Command, args []string) {
16+
color.Cyan("Logging out...")
1417
// Call the logout function from the auth package
1518
auth.Logout()
1619
},

cmd/publish.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
"rules-cli/internal/auth"
1111
"rules-cli/internal/registry"
1212

13+
"github.com/fatih/color"
1314
"github.com/spf13/cobra"
1415
)
1516

@@ -86,14 +87,14 @@ func runPublishCommand(cmd *cobra.Command, args []string) error {
8687
client.SetAuthToken(authConfig.AccessToken)
8788

8889
// Publish the rule
89-
fmt.Printf("Publishing rule to %s/%s with visibility: %s\n", ownerSlug, ruleSlug, visibility)
90+
color.Cyan("Publishing rule to %s/%s with visibility: %s", ownerSlug, ruleSlug, visibility)
9091
err = client.PublishRule(ownerSlug, ruleSlug, string(content), visibility)
9192
if err != nil {
9293
return fmt.Errorf("failed to publish rule: %w", err)
9394
}
9495

9596
ruleFileName := filepath.Base(ruleFilePath)
96-
fmt.Printf("Successfully published rule '%s' to %s/%s\n", ruleFileName, ownerSlug, ruleSlug)
97+
color.Green("Successfully published rule '%s' to %s/%s", ruleFileName, ownerSlug, ruleSlug)
9798
return nil
9899
}
99100

cmd/remove.go

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,11 @@ import (
66
"path/filepath"
77
"strings"
88

9-
"github.com/spf13/cobra"
109
"rules-cli/internal/formats"
1110
"rules-cli/internal/ruleset"
11+
12+
"github.com/fatih/color"
13+
"github.com/spf13/cobra"
1214
)
1315

1416
var (
@@ -66,22 +68,22 @@ For GitHub repositories, use the same gh: prefix as when adding.`,
6668

6769
// Check if we should prompt for confirmation
6870
if !forceFlag {
69-
fmt.Printf("This will remove rule '%s' (version %s) and delete its files. Continue? [y/N]: ", ruleName, version)
71+
color.Yellow("This will remove rule '%s' (version %s) and delete its files. Continue? [y/N]: ", ruleName, version)
7072
var response string
7173
fmt.Scanln(&response)
7274

7375
if !strings.EqualFold(response, "y") && !strings.EqualFold(response, "yes") {
74-
fmt.Println("Operation cancelled")
76+
color.Yellow("Operation cancelled")
7577
return nil
7678
}
7779
}
7880

7981
// Delete rule directory and files
8082
if err := os.RemoveAll(ruleDir); err != nil {
81-
fmt.Printf("Warning: Failed to delete rule files: %v\n", err)
83+
color.Red("Warning: Failed to delete rule files: %v", err)
8284
// Continue anyway to remove from rules.json
8385
} else {
84-
fmt.Printf("Deleted rule files from %s\n", ruleDir)
86+
color.Cyan("Deleted rule files from %s", ruleDir)
8587
}
8688
}
8789

@@ -91,7 +93,7 @@ For GitHub repositories, use the same gh: prefix as when adding.`,
9193
return fmt.Errorf("failed to save ruleset: %w", err)
9294
}
9395

94-
fmt.Printf("Rule '%s' (version %s) removed successfully\n", ruleName, version)
96+
color.Green("Rule '%s' (version %s) removed successfully", ruleName, version)
9597
return nil
9698
},
9799
}

0 commit comments

Comments
 (0)