Skip to content

Configuration

You can configure Rulesync by creating a rulesync.jsonc file in the root of your project.

JSON Schema Support

Rulesync provides a JSON Schema for editor validation and autocompletion. Add the $schema property to your rulesync.jsonc:

jsonc
// rulesync.jsonc
{
  "$schema": "https://github.com/dyoshikawa/rulesync/releases/latest/download/config-schema.json",
  "targets": ["claudecode"],
  "features": ["rules"],
}

Configuration Options

Example:

jsonc
// rulesync.jsonc
{
  "$schema": "https://github.com/dyoshikawa/rulesync/releases/latest/download/config-schema.json",

  // List of tools to generate configurations for. You can specify "*" to generate all tools.
  "targets": ["cursor", "claudecode", "geminicli", "opencode", "codexcli"],

  // Features to generate. You can specify "*" to generate all features.
  "features": ["rules", "ignore", "mcp", "commands", "subagents", "hooks"],

  // Alternatively, you can use object format to specify features per target:
  // "features": {
  //   "claudecode": ["rules", "commands"],
  //   "cursor": ["rules", "mcp"],
  // },

  // Output root directories to generate files into.
  // Basically, you can specify `["."]` only.
  // However, for example, if your project is a monorepo and you have to launch the AI agent at each package directory, you can specify multiple output roots.
  //
  // The legacy field name `baseDirs` is still accepted as a deprecated alias
  // and will be removed in a future major release. Migrate to `outputRoots`.
  "outputRoots": ["."],

  // Delete existing files before generating
  "delete": true,

  // Verbose output
  "verbose": false,

  // Silent mode - suppress all output (except errors)
  "silent": false,

  // Advanced options
  "global": false, // Generate for global(user scope) configuration files
  "simulateCommands": false, // Generate simulated commands
  "simulateSubagents": false, // Generate simulated subagents
  "simulateSkills": false, // Generate simulated skills

  // When true (default), `rulesync gitignore` only emits entries for the
  // tools listed in `targets`. Set to false to emit entries for all supported
  // tools regardless of `targets`.
  //
  // Note: Entries for `agentsmd` (AGENTS.md and related paths) are always
  // appended even when `gitignoreTargetsOnly` is true and `agentsmd` is
  // absent from `targets`. AGENTS.md is a de facto standard read by many AI
  // tools regardless of the target set, so its gitignore entries are emitted
  // unconditionally to prevent accidental commits of generated rule files.
  "gitignoreTargetsOnly": true,

  // Declarative skill sources — installed via 'rulesync install'
  // See the "Declarative Skill Sources" section for details.
  // "sources": [
  //   { "source": "owner/repo" },
  //   { "source": "org/repo", "skills": ["specific-skill"] },
  // ],
}

Per-Target Features

The targets option accepts both an array and an object format. Use the object format when you want to declare per-target feature configuration in a single place — the object keys are the target tools, and each value carries the features to generate for that tool:

jsonc
// rulesync.jsonc
{
  "targets": {
    "claudecode": ["rules", "commands"],
    "cursor": ["rules", "mcp"],
    "copilot": ["rules", "subagents"],
  },
}

In this example:

  • claudecode generates rules and commands
  • cursor generates rules and MCP configuration
  • copilot generates rules and subagents

Important: When targets is in object form, the top-level features field must be omitted. Declaring both would double-define the target set, so the config loader rejects that combination.

You can also use * (wildcard) inside a target's value to enable every feature for that tool:

jsonc
{
  "targets": {
    "claudecode": ["*"], // Generate all features for Claude Code
    "cursor": ["rules"], // Only rules for Cursor
  },
}

Per-feature options

Some features accept additional configuration. To pass options through, use the object form for a target's value instead of an array. Each feature key maps to either true/false (enable/disable) or an options object.

jsonc
{
  "gitignoreDestination": "gitignore",
  "targets": {
    "claudecode": {
      "gitignoreDestination": "gitattributes",
      "rules": { "ruleDiscoveryMode": "explicit" },
      "ignore": {
        "fileMode": "local",
        "gitignoreDestination": "gitignore",
      },
    },
  },
}

gitignoreDestination controls where rulesync gitignore writes path entries. You can set it:

  • at root level (gitignoreDestination)
  • at tool level (targets.<tool>.gitignoreDestination)
  • or at tool × feature level (targets.<tool>.<feature>.gitignoreDestination)

Allowed values:

  • "gitignore" (default)
  • "gitattributes"

Priority is more specific wins:

  1. tool × feature level
  2. tool level
  3. root level
  4. default ("gitignore")

Deprecated: object form under features

Earlier versions of Rulesync accepted per-target configuration under the top-level features field, paired with a targets array. That form is still parsed for backward compatibility but emits a deprecation warning; new configs should use the targets object form shown above.

⚠️ Breaking change in v8.0.0: mixing targets (array) with features (object) is no longer accepted — the config loader throws. If your config previously looked like targets: ["claudecode"], features: { claudecode: {...} }, migrate to the targets object form (recommended) or drop the targets array and keep only the features object (deprecated path). The migration is mechanical — see the example below.

jsonc
// ⚠️  Deprecated — still works, logs a warning
{
  "features": {
    "claudecode": { "rules": true, "ignore": { "fileMode": "local" } },
  },
}

To silence the deprecation warning (for example, in CI pipelines that intentionally run on the deprecated form until the migration is scheduled), set the RULESYNC_SILENT_DEPRECATION environment variable to any truthy value:

bash
RULESYNC_SILENT_DEPRECATION=1 npx rulesync generate

The current per-feature options are:

TargetFeatureOptionValuesDefault
claudecoderulesruleDiscoveryMode"none" / "explicit"tool default
anyrulesincludeLocalRoottrue / false (when false, localRoot rules are skipped for this target)true
claudecodeignorefileMode"shared" (settings.json) / "local" (settings.local.json)"shared"
anyanygitignoreDestination"gitignore" / "gitattributes""gitignore"

See docs/reference/file-formats.md for the rationale behind the Claude Code default and when to switch to "local".

Local Configuration

Rulesync supports a local configuration file (rulesync.local.jsonc) for machine-specific or developer-specific settings. This file is automatically added to .gitignore by rulesync gitignore and should not be committed to the repository.

Configuration Priority (highest to lowest):

  1. CLI options
  2. rulesync.local.jsonc
  3. rulesync.jsonc
  4. Default values

Example usage:

jsonc
// rulesync.local.jsonc (not committed to git)
{
  "$schema": "https://github.com/dyoshikawa/rulesync/releases/latest/download/config-schema.json",
  // Override targets for local development
  "targets": ["claudecode"],
  // Enable verbose output for debugging
  "verbose": true,
}

Target Order and File Conflicts

When multiple targets write to the same output file, the last target in the array wins. This is the "last-wins" behavior.

For example, both agentsmd and opencode generate AGENTS.md:

jsonc
{
  // opencode wins because it comes last
  "targets": ["agentsmd", "opencode"],
  "features": ["rules"],
}

In this case:

  1. agentsmd generates AGENTS.md first
  2. opencode generates AGENTS.md second, overwriting the previous file

If you want agentsmd's output instead, reverse the order:

jsonc
{
  // agentsmd wins because it comes last
  "targets": ["opencode", "agentsmd"],
  "features": ["rules"],
}

Released under the MIT License.