Java → C# translation: an idiomatic C# printer driven by the modification and nullability analyses
メンテナーはふだん 1 日以内に返信
まだ誰も着手していません。
評価
- 難易度
- 5/5
- 見積もり時間
- 1週間以上
- 初心者へのやさしさ
- 8/100
調査の方向性
Start by reading the Kotlin printer, maddi-cst-print-kotlin, and its JavaToKotlinRatchet, KotlinPrintMessage and NullabilityVerdicts seam, since the issue says the C# printer mirrors them. The first step is the new maddi-cst-print-csharp module with its TypePrinter/MethodPrinter/FieldPrinter implementations and a csharp-printing.md design doc. The issue does not define a finished state beyond the six-step plan, so a newcomer should not start here.
索引モデルが issue の本文から書いたものです。
説明
Goal
Translate Java to idiomatic C#, automatically: parse with the openjdk front end, print the CST as C# with a new maddi-cst-print-csharp module, and judge the result with the C# compiler. This is the C# counterpart of the Java → Kotlin translation (maddi-cst-print-kotlin, JavaToKotlinRatchet).
This is the printer direction. #111 covers the opposite direction (a Roslyn front end reading C#) and lists a C# printer as out of scope. Nothing here depends on #111's plan: the struct spike, the Predefined refactor and the exporter are front-end work. A Java-parsed CST is JVM-shaped, and the printer starts from that.
What drives it: the analyses
What sets this apart from a syntax converter is that maddi's analyses decide the output:
- Nullability (
NullabilityPassin maddi-mod) decides where?goes on reference types under#nullable enable, and where!,?.or??appear. TheNullabilityVerdictsseam thatmaddi-cst-print-kotlinuses carries over directly. - Modification and immutability decide whether something can be
readonly,init-only orIReadOnlyList<T>/IReadOnlyDictionary<K,V>, whether a class can become arecord, and whether a value type (readonly struct) is safe. Where the analysis proves code doesn't modify something, the C# says so. - Prepwork (
getSetField) collapses getters and setters into C# properties, as it does for Kotlin.
Without verdicts the printer still produces valid C#, just less precise: every reference is nullable-oblivious and every collection mutable.
Automation
The translation has to run without manual editing. It is measured the way J2K is: a ratchet per corpus (fernflower first) that translates the main sources, compiles them with dotnet build / Roslyn, and records syntax errors, semantic errors, compiling files and eventually passing tests. A metric that gets worse fails, and one that gets better must be written into the ratchet file. A shape the printer can't translate gets a named message (as KotlinPrintMessage does), never silently wrong output.
Harder than Kotlin
- No JVM interop. Kotlin can call the JDK and the corpus's original classes; C# can't. JDK references need a BCL mapping or a small runtime shim (
java.util.*,Stringmembers, streams → LINQ, exceptions, boxing). This mapping is the bulk of the work. It also means there is no "compile against the original classes" stage: the whole corpus has to translate first. - Semantic gaps:
- checked exceptions are dropped;
- wildcards (
? extends/? super) on reified generics; - non-static inner classes need an explicit outer reference;
- anonymous classes become nested classes, or lambdas/delegates for functional interfaces;
- enums with fields or bodies become classes;
- Java methods are virtual by default, so C# needs
virtual/override/sealed; >>>, integer andcharconversions, stringswitch, labelledbreak/continue(→goto).
Plan
maddi-cst-print-csharp: printers on the cst-apiTypePrinter/MethodPrinter/FieldPrinterinterfaces, reusingOutputElementandFormatter2; aCommonJavaToCSharptest base; acsharp-printing.mddesign document.- Syntax coverage of every statement and expression form, plus a
JavaToCSharpRatcheton fernflower counting syntax errors. - Structure and the JDK → BCL mapping: semantic errors, then compiling files.
- Nullability verdicts →
#nullable enableoutput, with a ratchet in maddi-mod (likeTestJavaToKotlinFernflowerNullability). - Modification/immutability verdicts →
readonly, read-only collection interfaces, records. - The corpus's tests, translated, passing.
- 主要言語
- Java
- スター
- 1
- フォーク
- 1
- 平均マージ
- 1時間 55分
- マージ済み PR(30日)
- 8
環境構築
- Dockerfile・Docker Compose ファイルなし
- プルリクエストのテンプレートあり
- コントリビューションガイドを読む
はじめの一歩
- issue を最後まで読み、次にプロジェクトのコントリビューションガイドを読みます。
- 着手することを issue にコメントします — 二人が同じ作業をするのを防げます。
- リポジトリをフォークし、ブランチを切って変更します。
- issue 番号を参照したプルリクエストを送ります。
CodeLaser/maddi のほかの issue
-
難易度 2/5 1〜3時間 初心者へのやさしさ 78/100
CodeLaser/maddi#166 · コメント 2 件 ·
メンテナーはふだん 1 日以内に返信
-
build/ci good first issue
難易度 2/5 1〜3時間 初心者へのやさしさ 72/100
メンテナーはふだん 1 日以内に返信
-
難易度 4/5 3〜5日 初心者へのやさしさ 38/100
メンテナーはふだん 1 日以内に返信
-
bug
難易度 3/5 1〜2日 初心者へのやさしさ 65/100
メンテナーはふだん 1 日以内に返信
-
bug
難易度 3/5 1〜2日 初心者へのやさしさ 68/100
メンテナーはふだん 1 日以内に返信
CodeLaser/maddi の issue をすべて見る
似ている issue
-
難易度 2/5 1〜3時間 初心者へのやさしさ 72/100
geonetwork/core-geonetwork#9592 ·
メンテナーはふだん 2 日以内に返信
-
難易度 2/5 1〜3時間 初心者へのやさしさ 75/100
NationalSecurityAgency/ghidra#10040 ·
メンテナーはふだん 2 日以内に返信
-
難易度 2/5 1〜3時間 初心者へのやさしさ 63/100
メンテナーはふだん 1 日以内に返信
-
[Bug] ServerHttpRequest.getURI() throws NumberFormatException when Host contains an explicit portオープンcomponent/need-triage type/need-triage
難易度 2/5 1〜3時間 初心者へのやさしさ 76/100
メンテナーはふだん 1 日以内に返信
-
bug
難易度 2/5 1〜3時間 初心者へのやさしさ 72/100
apache/rocketmq-dashboard#7361 ·
メンテナーはふだん 3 日以内に返信