<html><body><div dir="ltr">JEP 445 does a ton of work cleaning up that experience of ‘meeting java for the first time’. I fear the herculean effort required for the bazillion tutorials and books out there to adopt this new style, but no time like the present to start that work.<div><br></div><div dir="ltr">But, java is just about the least structurally typed language I’m aware of. It even insists functions have a type name (lambdas aren’t legit unless context allows the compiler to treat them as a functional interface).<br></div><div dir="ltr"><br></div><div dir="ltr">There are only 4 exceptions baked into java itself:</div><div dir="ltr"><br></div><div dir="ltr">(1) main().</div><div dir="ltr"><br></div><div dir="ltr">(2) agentmain().</div><div dir="ltr"><br></div><div dir="ltr">(3) serialization, which brings in 5x structural typing (serialVersionUID field, writeReplace, readResolve, writeObject, and readObject).</div><div dir="ltr"><br></div><div dir="ltr">(4) The beanspec. Clearly the JDK doesn’t care about it given that records decided to go with <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">property()</code> instead of <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">getProperty()</code>.</div><div dir="ltr"><br></div><div dir="ltr">Given the repeated strong discouragement from OpenJDK about those last 2, that really just leaves main and agentmain, and given that agents are more or less rocket science (in the sense that only quite seasoned java programmers are likely to ever get assigned the job of writing an agent), that really <b>just leaves main() as the one and only place in the entire java ecosystem where structural typing is a thing</b>.</div><div dir="ltr"><br></div><div dir="ltr">Which is really, really, weird. It’s the very first method someone being introduced to java is ever going to write, and it therefore -immediately- sends new programmers down the wrong path. When you meet java for the first time, you meet an aspect of java that is literally not how anything else in java works.</div><div dir="ltr"><br></div><div dir="ltr">The <i>reasons</i> for it are obvious enough: Like <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">switch</code> syntax, it’s a holdover from C - it was familiar to C programmers, java did indeed manage to become one of the most popular languages in fairly short order and during a time when C was incredibly popular, so this is no complaint about java’s past choices: Who knows where java would be today if it hadn’t chosen to emulate C syntax as much as possible even in cases where it was a highly dubious choice, even in historical context (who likes original switch syntax? Surely that was always horrible. This structural typing thing similarly is just bizarre).</div><div dir="ltr"><br></div><div dir="ltr">But, if a JEP comes along to fix it, let’s… fix it. If possible. Which may just be too difficult, in the sense that fixing it requires even more deviation from what java programmers are used to. Then again, the point of JEP445 is surely mostly about those new to java and far less to cater to the needs of seasoned java programmers who are just slapping together a quick one-off script in java; they have tools that generate this stuff for you and/or have jshell or similar already installed if they run into this situation of needing a quickly fire-and-forget stand-alone java app more than once in a blue moon.</div><div dir="ltr"><br></div><div dir="ltr">Should look something like:<br><span style="white-space:pre-wrap"><br></span></div><div dir="ltr">package java.lang;<br></div><div dir="ltr">public interface Application {<br></div><div dir="ltr"> void main() throws Exception;</div><div dir="ltr">}</div><div dir="ltr"><br></div><div dir="ltr">and to use, of course:</div><div dir="ltr"><br></div><div dir="ltr">class MyApp implements Application {</div><div dir="ltr"> public void main() {</div><div dir="ltr"> }</div><div dir="ltr">}</div><div dir="ltr"><br></div><div dir="ltr">An obvious issue here is that it eliminates some of the gains JEP445 just set up for us. Even taking into account that in the vein of JEP445, <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">class MyApp implements Application</code> is made optional, the lang spec still requires you to make that <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">main</code> method public. Decreeing via JEP that you don’t have to is perhaps pushing things a little too close into the “voodoo magic” column.</div><div dir="ltr"><br></div><div dir="ltr">But, it does open up an opportunity to fix the rest of those first minutes of meeting java in a far cleaner fashion.</div><div dir="ltr"><br></div><div dir="ltr"><code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">Scanner</code> is 90%+ suggested as the thing to use when writing keyboard-interactive apps, and keyboard-interactive apps are 90%+ of all first-steps java apps. SOURCE: Answering a ton of questions on stack overflow, and searching the web for some java tutorials, <i>all</i> of which mention Scanner very early on. Which is a problem - because as far as I can tell Scanner was never designed primarily for keyboard input! - Or at least I hope not or it can vie for the dubious honour of being the most unfit-for-stated-purpose core API library vs, I guess, <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">java.util.Calendar</code> or some other sordid historic artefact of the core libs.<br></div><div dir="ltr"><br></div><div dir="ltr">If <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">Application</code> is set up to look something like this:</div><div dir="ltr"><br></div><div dir="ltr">public interface TerminalInteractive {</div><div dir="ltr"> int promptInt(String prompt);</div><div dir="ltr"> String promptString(String prompt);</div><div dir="ltr"> String promptPassword(String prompt);</div><div dir="ltr"> void print(String text); // no more need for printf due to JEP about formatters, maybe?</div><div dir="ltr"> void exit(int returnCode);<br></div><div dir="ltr"> // you get the idea</div><div dir="ltr"> // possibly some command line parsing tooling is appropriate here, too?</div><div dir="ltr">}</div><div dir="ltr"><br></div><div dir="ltr">and Application itself is turned into:</div><div dir="ltr"><br></div><div dir="ltr">public abstract class Application {</div><div dir="ltr"> protected TerminalInteractive terminal;</div><div dir="ltr"> </div><div dir="ltr"> protected abstract void main();</div><div dir="ltr">}</div><div dir="ltr"><br></div><div dir="ltr"><br></div><div dir="ltr">with an additional rule that on boot a JVM will properly initialize the <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">terminal</code> field (or terminal is exposed in some other fashion to Application classes, the above is to serve as inspiration and not a fully fleshed out proposal), all those pesky issues with first-steps java (or at least, 90%+ of what beginners are asking questions about) disappear. It also gets rid of some more utterly unlike anything else in the entire ecosystem aspects of java, such as <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.in</code> and <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.out</code> and <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.err</code> which are public static fields (very rare in the java ecosystem), marked final, which are nevertheless not at all final but you have to modify them using <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.setOut</code> and friends which is - unique. In a bad way. Even just writing <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.out.println</code> ends up not looking like anything else in the ecosystem and is sending folks learning java down the wrong path. Nothing in java is like this. If you start designing APIs, do not design them like <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">System.out</code>.</div><div dir="ltr"><br></div><div dir="ltr">I’m not sure it’s worthwhile talking about simplifying main classes if ‘how does one emit text and read stuff from the command line’ is not just ‘out of scope’ but ‘beyond even considering’, given that it seems self evident that virtually all main apps break down into one of two camps:</div><div dir="ltr"><br></div><div dir="ltr">(1) They are merely the entrypoint to hundreds of thousands+ lines of code, such as a webserver that reads in routing tables and starts serving, or, say, Eclipse, or IntelliJ. Trying to simplify them is irrelevant; not at all what JEP445 is targeting, surely.</div><div dir="ltr"><br></div><div dir="ltr">(2) A very simple app, possibly (probably) somebody learning java. In which case terminal interaction is virtually guaranteed to be very relevant.</div><div dir="ltr"><br></div><div dir="ltr"><br></div><div dir="ltr">These concepts can be handwaved away as out of scope, but if that’s done I don’t think this JEP fully accomplishes what it should. Teaching someone how to write ‘hello world’ in java will still involve <i>multiple</i> completely bizarre (in the sense that <i>nothing</i> in the java ecosystem works like that) concepts. And will soon lead to very commonly asked questions because the very first API they run into (Namely, Scanner) is very badly written API for the needs that these first steps programmers have. JEP445 as-is is still useful: Getting rid of <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">static</code> is <i>very</i> worthwhile (again, dealing with newbie questions is the primary source for this, as <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">static</code> causes a ton of confusion and leads very significant first-steps java programmers down the wrong path, making everything they write <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">static</code> because if they do not “the compiler complains about 'something something something static context’"), but other than allowing <code style="border:1px solid rgb(206,206,206);background-color:rgb(244,244,244);padding:0px 2px;border-radius:2px">main</code> to be non-static, the rest of JEP445 doesn’t seem to accomplish meaningful change without addressing structural typing and the API used to interact with sysout/err/in.</div><div dir="ltr"><br></div><div dir="ltr">Treating the JEP as merely steps along the way to perfection feels like making a choice that OpenJDK will later regret, by enshrining into spec even further the notion of a structurally typed main method.</div><div dir="ltr"><br></div><div dir="ltr"></div><div dir="ltr"></div></div></body></html>