# Key Data Models in Alibaba Open Code Review: A Complete Guide

> Explore Alibaba Open Code Review's key data models like Diff, ScanItem, and LlmComment. Understand the core structs powering the code review pipeline from diff parsing to LLM suggestions.

- Repository: [Alibaba/open-code-review](https://github.com/alibaba/open-code-review)
- Tags: deep-dive
- Published: 2026-08-04

---

**Alibaba's Open Code Review (OCR) tool relies on seven core domain structs—`Diff`, `ScanItem`, `LlmComment`, `CodeReviewResult`, `Preview`, `PreviewEntry`, and `ExcludeReason`—to orchestrate the code review pipeline from Git diff parsing to LLM-generated suggestions.**

The `alibaba/open-code-review` repository implements a CLI-driven code review system that uses structured data models to bridge Git operations, LLM inference, and user interfaces. Understanding these **open code review data models** is essential for developers extending the tool or integrating it into custom workflows. The models are defined in the `internal/model` package and designed to be JSON-serializable for seamless communication between components.

## Core Data Models in Open Code Review

### Diff – Representing File Changes

The **`Diff`** struct is the foundational unit for code changes. Defined in [`internal/model/diff.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/diff.go), it captures metadata about a single file modification including path changes, binary status, and line statistics. The struct contains fields such as `OldPath`, `NewPath`, `Diff` (the raw unified-diff text), `NewFileContent`, boolean flags for `IsBinary`, `IsDeleted`, `IsNew`, and `IsRenamed`, plus counters for `Insertions` and `Deletions`. The Git diff parser in [`internal/diff/parser.go`](https://github.com/alibaba/open-code-review/blob/main/internal/diff/parser.go) generates slices of these structs to feed the review pipeline.

### ScanItem – Full-File Scanning

When operating in full-scan mode (reviewing entire files rather than just changes), the system uses the **`ScanItem`** struct from [`internal/model/scan.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/scan.go). It stores the `Path`, `Content`, `IsBinary` flag, and `LineCount`. Crucially, the `AsDiff()` method converts a `ScanItem` into a `Diff` object, allowing the same downstream processing logic to handle both differential and full-file reviews uniformly.

### LLM Output Models

The review engine produces structured feedback through two related models defined in [`internal/model/review.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/review.go):

**`CodeReviewResult`** acts as a lightweight wrapper for raw LLM output, containing `RelevantFile`, `SuggestionContent`, `ExistingCode`, and `SuggestionCode`. This intermediate representation is subsequently transformed into the richer **`LlmComment`** struct, which adds metadata essential for display and actionability: `Path`, `Content`, `SuggestionCode`, `ExistingCode`, line ranges (`StartLine`, `EndLine`), `Thinking` (chain-of-thought), `Category` (e.g., "bug", "style"), and `Severity` (e.g., "high", "medium").

### Preview System

Before executing a review, the CLI displays a preview table using three coordinated models from [`internal/model/preview.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/preview.go):

The **`ExcludeReason`** enumeration defines why files are skipped: `ExcludeUserRule`, `ExcludeExtension`, `ExcludeDefaultPath`, `ExcludeDeleted`, `ExcludeBinary`, or `ExcludeNone`. Each **`PreviewEntry`** represents one file in the preview table with fields for `Path`, `Status`, `Insertions`, `Deletions`, `WillReview` boolean, and the `ExcludeReason`. Finally, the **`Preview`** struct aggregates all entries, calculating `TotalInsertions`, `TotalDeletions`, `TotalFiles`, `ReviewableCount`, and `ExcludedCount` for the `opencodereview preview` command output.

## Architectural Data Flow

The data models interact in a five-stage pipeline that maintains type safety across the boundary between Git operations and LLM processing:

1. **Git Parsing**: The parser in [`internal/diff/parser.go`](https://github.com/alibaba/open-code-review/blob/main/internal/diff/parser.go) produces `[]Diff` from repository changes.
2. **Mode Unification**: In scan mode, [`internal/scan/agent.go`](https://github.com/alibaba/open-code-review/blob/main/internal/scan/agent.go) generates `ScanItem` instances and calls `AsDiff()` to normalize them into the diff pipeline.
3. **Preview Generation**: The system constructs a `Preview` object containing `PreviewEntry` slices, applying exclusion logic and calculating aggregate statistics.
4. **LLM Processing**: The loop in [`internal/llmloop/loop.go`](https://github.com/alibaba/open-code-review/blob/main/internal/llmloop/loop.go) consumes `Diff` objects, generates `CodeReviewResult` instances from the LLM, and marshals them into `LlmComment` objects with full metadata.
5. **Output Rendering**: The CLI or web UI renders the final `LlmComment` slices, optionally writing suggestions back via the `gitcmd` package.

## Working with the Models

### Converting ScanItem to Diff

When implementing custom scanners, convert full-file content to the diff format using the `AsDiff()` method:

```go
import "github.com/alibaba/open-code-review/internal/model"

// Create a ScanItem from file system traversal
item := &model.ScanItem{
    Path:      "src/main.go",
    Content:   fileContent,
    IsBinary:  false,
    LineCount: len(strings.Split(fileContent, "\n")),
}

// Normalize to Diff for pipeline compatibility
diff := item.AsDiff()

```

### Building Preview Tables

Construct preview summaries to validate which files will be reviewed before invoking the LLM:

```go
func buildPreview(diffs []model.Diff) *model.Preview {
    preview := &model.Preview{}
    for _, d := range diffs {
        entry := model.PreviewEntry{
            Path:       d.NewPath,
            Status:     "modified",
            Insertions: d.Insertions,
            Deletions:  d.Deletions,
            WillReview: true,
        }
        preview.Entries = append(preview.Entries, entry)
        preview.TotalInsertions += d.Insertions
        preview.TotalDeletions += d.Deletions
    }
    preview.TotalFiles = len(diffs)
    preview.ReviewableCount = len(diffs)
    return preview
}

```

### Generating LLM Comments

Transform raw LLM results into structured comments with metadata:

```go
func toLlmComment(res model.CodeReviewResult) *model.LlmComment {
    return &model.LlmComment{
        Path:           res.RelevantFile,
        Content:        res.SuggestionContent,
        SuggestionCode: res.SuggestionCode,
        ExistingCode:   res.ExistingCode,
        StartLine:      10,
        EndLine:        12,
        Category:       "bug",
        Severity:       "high",
    }
}

```

## Summary

- The **`Diff`** struct in [`internal/model/diff.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/diff.go) represents individual file changes with full metadata and content.
- **`ScanItem`** enables full-file scanning mode and converts to `Diff` via `AsDiff()` for pipeline uniformity.
- **`CodeReviewResult`** and **`LlmComment`** handle LLM output, with the latter providing rich metadata including severity, category, and line ranges.
- The **`Preview`**, **`PreviewEntry`**, and **`ExcludeReason`** types in [`internal/model/preview.go`](https://github.com/alibaba/open-code-review/blob/main/internal/model/preview.go) manage pre-review filtering and statistics.
- All models are JSON-serializable, enabling loose coupling between the CLI, HTTP API, and LLM worker components.

## Frequently Asked Questions

### What is the difference between Diff and ScanItem in Open Code Review?

The **`Diff`** struct represents changes extracted from Git diffs, containing fields like `OldPath`, `NewPath`, and insertion/deletion counts. The **`ScanItem`** struct represents entire files in full-scan mode, storing `Path`, `Content`, and `LineCount`. The `ScanItem.AsDiff()` method converts scan items into diffs, allowing both modes to share the same review pipeline in [`internal/llmloop/loop.go`](https://github.com/alibaba/open-code-review/blob/main/internal/llmloop/loop.go).

### How does the Preview model determine which files to review?

The **`Preview`** model aggregates **`PreviewEntry`** structs, each containing a `WillReview` boolean and an **`ExcludeReason`** enumeration. Files are excluded based on user rules, unsupported extensions, default paths, binary status, or deletion status. The preview calculation occurs before the LLM loop begins, allowing users to verify the review scope via the `opencodereview preview` command.

### What information does an LlmComment contain?

An **`LlmComment`** captures a complete review suggestion with the file `Path`, review `Content`, `SuggestionCode` for fixes, `ExistingCode` for context, line ranges (`StartLine`, `EndLine`), and classification metadata including `Category` (e.g., "performance") and `Severity` (e.g., "critical"). It also stores the LLM's `Thinking` chain-of-thought for transparency.

### Where are the data models defined in the Open Code Review repository?

All core data models reside in the `internal/model` directory: [`diff.go`](https://github.com/alibaba/open-code-review/blob/main/diff.go) contains the `Diff` struct, [`scan.go`](https://github.com/alibaba/open-code-review/blob/main/scan.go) defines `ScanItem`, [`review.go`](https://github.com/alibaba/open-code-review/blob/main/review.go) houses `LlmComment` and `CodeReviewResult`, and [`preview.go`](https://github.com/alibaba/open-code-review/blob/main/preview.go) contains `Preview`, `PreviewEntry`, and `ExcludeReason`. The parser in [`internal/diff/parser.go`](https://github.com/alibaba/open-code-review/blob/main/internal/diff/parser.go) and the scan agent in [`internal/scan/agent.go`](https://github.com/alibaba/open-code-review/blob/main/internal/scan/agent.go) instantiate these models during the review workflow.