Diff Viewer
The DiffViewer component provides a powerful way to display file differences with syntax highlighting. It supports both Split (side-by-side) and Unified (inline) display modes, making it perfect for code review interfaces, version comparison tools, and change visualization.
Usage
import { DiffViewer } from "@harnessio/ui/components";
function MyComponent() { const oldCode = `function hello() {\n console.log("Hello");\n}`; const newCode = `function hello(name) {\n console.log(\`Hello \${name}\`);\n}`;
return <DiffViewer oldCode={oldCode} newCode={newCode} lang="typescript" />;}Note: The DiffViewer requires ThemeProvider from @harnessio/ui/context to be present in your component tree for theme detection to work properly.
Features
- Split & Unified Modes - View diffs side-by-side or inline
- Syntax Highlighting - Powered by Shiki with support for 200+ languages
- Theme Support - Automatically adapts to light/dark theme via ThemeProvider context
- Real-time Theme Switching - Updates instantly when theme changes without page refresh
- Line Numbers - Clear line number indicators for both old and new code
- Change Indicators - Visual markers for additions, deletions, and modifications
- Responsive - Works seamlessly across different screen sizes
Props
Prop | Required | Default | Type |
|---|---|---|---|
| oldCode | true | string | |
| newCode | true | string | |
| lang | false | 'yaml' | DiffHighlighterLang |
| diffViewWrap | false | false | boolean |
Language Support
The component supports syntax highlighting for 200+ programming languages through the Shiki highlighter.
Popular Languages
- Web Development:
typescript,tsx,javascript,jsx,html,css,scss,less,vue,vue-html - Backend:
python,go,java,csharp,php,ruby,rust,kotlin,swift - Data & Config:
yaml,json,xml,ini,properties,sql,graphql - Shell & Scripts:
bash,shell,powershell,dockerfile,makefile - Documentation:
markdown,asciidoc,latex - Systems:
c,cpp,objectivec,rust,go,assembly
Supported Languages
The component supports all languages from the Shiki/Highlight.js library including:
arduino, bash, c, cpp, csharp, css, diff, go, graphql, ini, java, javascript, jsx, json, kotlin, less, lua, makefile, markdown, objectivec, perl, php, plaintext, python, r, ruby, rust, scss, shell, sql, swift, typescript, tsx, vbnet, wasm, xml, yaml, vue, vue-html, actionscript, ada, apache, applescript, armasm, awk, clojure, cmake, coffeescript, crystal, dart, delphi, django, dockerfile, elixir, elm, erlang, fortran, fsharp, gherkin, glsl, gradle, groovy, haml, handlebars, haskell, haxe, julia, latex, lisp, llvm, matlab, nginx, nim, nix, ocaml, perl, pgsql, prolog, protobuf, puppet, scala, scheme, smalltalk, stylus, tcl, terraform, twig, verilog, vhdl, vim, and many more.
Total: 200+ languages supported
Display Modes
The DiffViewer currently uses Split mode by default, which displays the old and new code side-by-side for easy comparison.
Split Mode (Side-by-Side)
- Shows old code on the left, new code on the right
- Ideal for detailed line-by-line comparisons
- Best for desktop and larger screens
- Clear visual separation of changes
Theme Integration
The component automatically adapts to your application’s theme using the useTheme() hook:
Automatic Theme Detection
- The component reads the
isLightThemevalue from theThemeProvidercontext - Theme changes are detected automatically and the diff view updates in real-time
- No manual configuration needed - the theme synchronization happens automatically
- Supports all theme modes from the design system (dark/light with various contrast levels)
Best Practices
- Use Proper Language - Always specify the correct
langprop for accurate syntax highlighting - Format Code - Ensure code is properly formatted before passing to the component
- Use
\nfor Line Breaks - When defining code strings, use\nfor newlines - Keep Code Readable - For very large diffs, consider pagination or limiting the visible range
- Provide Context - Include enough surrounding code to make changes understandable
Examples
TypeScript Comparison
<DiffViewer oldCode={`interface User { name: string; age: number;}`} newCode={`interface User { name: string; email: string; age: number; isActive: boolean;}`} lang="typescript"/>JSON Configuration
<DiffViewer oldCode={`{ "version": "1.0.0", "name": "my-app"}`} newCode={`{ "version": "2.0.0", "name": "my-app", "description": "My awesome app"}`} lang="json"/>Python Code
<DiffViewer oldCode={`def greet(): print("Hello")`} newCode={`def greet(name="World"): print(f"Hello, {name}!")`} lang="python"/>Performance Considerations
The component is optimized for performance:
- Async Loading - Syntax highlighting is loaded asynchronously to avoid blocking
- Efficient Rendering - Large diffs are rendered efficiently without performance degradation
- Optimized Theme Switching - Theme changes don’t trigger unnecessary re-renders
- Memoization - Diff calculations are memoized to prevent redundant processing