<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Mr Smithnen</title>
    <description>The latest articles on DEV Community by Mr Smithnen (@marko_kseppnen_6250a7f).</description>
    <link>https://dev.to/marko_kseppnen_6250a7f</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3380051%2Fab905cdb-117b-4e21-8430-277edad4f061.jpg</url>
      <title>DEV Community: Mr Smithnen</title>
      <link>https://dev.to/marko_kseppnen_6250a7f</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/marko_kseppnen_6250a7f"/>
    <language>en</language>
    <item>
      <title>YINI Config Format reaches RC 6 - clearer strings, stricter parsing, and growing tooling ecosystem</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Fri, 19 Jun 2026 21:14:38 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-config-format-specification-rc-6-released-clearer-strings-stricter-parsing-and-growing-2n6k</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-config-format-specification-rc-6-released-clearer-strings-stricter-parsing-and-growing-2n6k</guid>
      <description>&lt;h2&gt;
  
  
  YINI Specification RC 6 is now released
&lt;/h2&gt;

&lt;p&gt;The YINI configuration format has reached &lt;strong&gt;Specification Release Candidate 6&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;YINI is a configuration format designed to feel familiar if you like INI-style files, but designed to bring more explicit structure, clarity, useful data types, and predictable parsing rules to real-world configuration needs..&lt;/p&gt;

&lt;p&gt;The short version:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@yini

^ App
name = "Example"
version = "1.0.0"
debug = false

^^ Server
host = "127.0.0.1"
port = 8080

^^ Features
enabled = [
    "auth",
    "logging",
    "metrics",
]
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;YINI tries to sit somewhere between classic INI, JSON, TOML, and YAML:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;More structured than traditional INI.&lt;/li&gt;
&lt;li&gt;Less punctuation-heavy than JSON.&lt;/li&gt;
&lt;li&gt;Indentation-insensitive unlike YAML.&lt;/li&gt;
&lt;li&gt;Explicit about parsing rules and validation behavior.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;RC 6 is an important release because it tightens several parts of the language and moves the format closer to a stable 1.0 specification.&lt;/p&gt;




&lt;h3&gt;
  
  
  What changed in RC 6?
&lt;/h3&gt;

&lt;p&gt;RC 6 includes a number of syntax and behavior updates. The main theme is the same as before:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Make the format clear for humans, but deterministic for parsers.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Here are some of the notable updates.&lt;/p&gt;




&lt;h3&gt;
  
  
  Clearer section markers
&lt;/h3&gt;

&lt;p&gt;YINI uses section markers to define structure.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
name = "MyApp"

^^ Server
host = "localhost"

^^^ TLS
enabled = true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The number of section markers defines the nesting level. This keeps hierarchy visible without relying on indentation.&lt;/p&gt;

&lt;p&gt;The primary section marker is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;YINI also supports alternative section markers, but &lt;code&gt;^&lt;/code&gt; remains the recommended default for most files and examples.&lt;/p&gt;




&lt;h3&gt;
  
  
  Strict and lenient mode behavior is more clearly defined
&lt;/h3&gt;

&lt;p&gt;YINI has two parsing modes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Lenient mode&lt;/strong&gt; — practical, forgiving, and intended as the default.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Strict mode&lt;/strong&gt; — validation-focused and intended for stricter tooling, CI checks, and production-sensitive configuration.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A file can declare its intended mode:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@yini strict
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;or:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@yini lenient
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;RC 6 clarifies how these declarations should behave when the file is parsed in a different mode.&lt;/p&gt;

&lt;p&gt;The goal is to avoid silent surprises. If a file says it expects strict behavior, tools should not quietly treat that as “close enough” in a looser context.&lt;/p&gt;




&lt;h3&gt;
  
  
  Comment syntax is more consistent
&lt;/h3&gt;

&lt;p&gt;YINI supports common comment styles:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# A line comment

// Another line comment

; A full-line comment

/*
    A block comment.
*/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;RC 6 clarifies comment behavior, including that &lt;code&gt;#&lt;/code&gt; is now consistently treated as a comment marker outside strings.&lt;/p&gt;

&lt;p&gt;This also affects number syntax, because &lt;code&gt;#&lt;/code&gt; is no longer used for hexadecimal numbers.&lt;/p&gt;




&lt;h3&gt;
  
  
  Hexadecimal numbers use clearer prefixes
&lt;/h3&gt;

&lt;p&gt;Instead of using &lt;code&gt;#&lt;/code&gt; for hexadecimal notation, YINI now uses clearer forms such as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;color = 0xffcc00
mask = hex:ffcc00
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This avoids conflict with comment syntax and makes the language easier to scan.&lt;/p&gt;

&lt;p&gt;Digit separators are also supported for readability:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;maxSize = 1_000_000
flags = 0b1111_0000
id = 0x_ab_cd_12_34
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h3&gt;
  
  
  String handling was simplified
&lt;/h3&gt;

&lt;p&gt;RC 6 continues to refine string behavior.&lt;/p&gt;

&lt;p&gt;YINI supports different string forms for different needs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;name = "Example"
path = R"C:\Users\marko\config"
message = C"Line one\nLine two"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The distinction between raw strings and classic escaped strings is important:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Raw strings preserve backslashes.&lt;/li&gt;
&lt;li&gt;Classic strings interpret escape sequences.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Triple-quoted strings are also available for longer text.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;description = """
This is a longer string.
It can span multiple lines.
"""
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The goal is to make string behavior explicit instead of surprising.&lt;/p&gt;




&lt;h3&gt;
  
  
  String concatenation is stricter and more predictable
&lt;/h3&gt;

&lt;p&gt;String concatenation uses &lt;code&gt;+&lt;/code&gt;, but RC 6 makes the rules more explicit.&lt;/p&gt;

&lt;p&gt;In strict mode, concatenation is intentionally conservative:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;title = "YINI " + "Config"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;All operands must be string literals.&lt;/p&gt;

&lt;p&gt;In lenient mode, scalar values may be allowed after the first string literal:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;message = "Port: " + 8080
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Result:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Port: 8080
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But this is still string concatenation only. It is not arithmetic.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;value = 1 + 2
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That should not be treated as numeric addition.&lt;/p&gt;

&lt;p&gt;This is one of the places where YINI deliberately favors predictability over cleverness.&lt;/p&gt;




&lt;h3&gt;
  
  
  Inline objects are more clearly specified
&lt;/h3&gt;

&lt;p&gt;YINI supports inline objects for compact structured values:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;database = {
    host: "localhost",
    port: 5432,
    ssl: true,
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;RC 6 clarifies the preferred object member syntax.&lt;/p&gt;

&lt;p&gt;The canonical form is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;key: value
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Lenient parsers may accept &lt;code&gt;key = value&lt;/code&gt; in inline objects, but strict mode should require &lt;code&gt;:&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;That gives users a friendly mode while still keeping strict mode suitable for validation.&lt;/p&gt;




&lt;h3&gt;
  
  
  Lists remain bracketed and explicit
&lt;/h3&gt;

&lt;p&gt;Lists use brackets:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;plugins = [
    "auth",
    "cache",
    "metrics",
]
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Trailing commas are convenient in hand-edited files and may be accepted in lenient mode.&lt;/p&gt;

&lt;p&gt;Strict mode can reject them if the specification requires stricter validation.&lt;/p&gt;

&lt;p&gt;Missing entries are not silently treated as &lt;code&gt;null&lt;/code&gt;. This is intentional. YINI should not guess structure that was not written.&lt;/p&gt;




&lt;h3&gt;
  
  
  Duplicate keys and sections are safer
&lt;/h3&gt;

&lt;p&gt;RC 6 keeps duplicate handling conservative.&lt;/p&gt;

&lt;p&gt;Duplicate keys in the same section and nesting level are not silently overwritten.&lt;/p&gt;

&lt;p&gt;In lenient mode, the first definition wins and later duplicates should produce a warning.&lt;/p&gt;

&lt;p&gt;In strict mode, duplicates are errors.&lt;/p&gt;

&lt;p&gt;This avoids one of the most frustrating configuration-file problems: a value being accidentally overridden far below the original definition.&lt;/p&gt;

&lt;p&gt;Duplicate sections are also not treated as implicit merges. YINI avoids hidden merge behavior because it can become hard to reason about in larger files.&lt;/p&gt;




&lt;h3&gt;
  
  
  Strict files can use a &lt;code&gt;.strict.yini&lt;/code&gt; suffix
&lt;/h3&gt;

&lt;p&gt;RC 6 also documents the recommended naming convention for strict-mode YINI files:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;config.strict.yini
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is not meant to replace the actual parser mode, but it gives humans and tools a useful signal.&lt;/p&gt;

&lt;p&gt;For example, a CI workflow or editor extension can warn if a file looks like it should be strict but is being parsed differently.&lt;/p&gt;




&lt;h3&gt;
  
  
  The YINI ecosystem is growing too
&lt;/h3&gt;

&lt;p&gt;Alongside the specification, there are now several related tools and repositories around the format.&lt;/p&gt;

&lt;p&gt;The main pieces include:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The YINI specification.&lt;/li&gt;
&lt;li&gt;A TypeScript parser.&lt;/li&gt;
&lt;li&gt;A Python parser.&lt;/li&gt;
&lt;li&gt;A CLI tool for parsing and converting YINI.&lt;/li&gt;
&lt;li&gt;Syntax highlighting support for editors using TextMate-style grammars.&lt;/li&gt;
&lt;li&gt;A public &lt;code&gt;yini-test&lt;/code&gt; test suite for parser behavior and compatibility checks.&lt;/li&gt;
&lt;li&gt;The YINI homepage and documentation.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The &lt;code&gt;yini-test&lt;/code&gt; repository is especially important because it gives parser implementations a shared set of cases to validate against. This helps keep behavior consistent across languages instead of each parser drifting in its own direction.&lt;/p&gt;

&lt;p&gt;The CLI is useful for trying YINI quickly:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx yini-cli parse config.yini
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The TypeScript parser can be used directly in Node.js or TypeScript projects, and the Python parser is also being developed for Python-based tooling and applications.&lt;/p&gt;




&lt;h3&gt;
  
  
  Why RC 6 matters
&lt;/h3&gt;

&lt;p&gt;RC 6 is not about adding flashy features.&lt;/p&gt;

&lt;p&gt;It is mostly about tightening the language:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Fewer ambiguous rules.&lt;/li&gt;
&lt;li&gt;Clearer strict vs lenient behavior.&lt;/li&gt;
&lt;li&gt;Safer duplicate handling.&lt;/li&gt;
&lt;li&gt;More explicit string behavior.&lt;/li&gt;
&lt;li&gt;Clearer number syntax.&lt;/li&gt;
&lt;li&gt;Better parser consistency.&lt;/li&gt;
&lt;li&gt;And stronger alignment between the specification and tooling.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That is the kind of work a configuration format needs before calling itself stable.&lt;/p&gt;

&lt;p&gt;A config format should be boring in the right ways. It should be easy to read, hard to misread, and predictable for tools.&lt;/p&gt;

&lt;p&gt;That is the direction YINI is aiming for.&lt;/p&gt;




&lt;h3&gt;
  
  
  Try it
&lt;/h3&gt;

&lt;p&gt;A minimal YINI file looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@yini

^ App
name = "Hello YINI"
debug = false

^^ Server
host = "127.0.0.1"
port = 8080
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Parse it with the CLI:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx yini-cli parse config.yini
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The result is structured data that can be exported as JSON or used by tools and applications.&lt;/p&gt;




&lt;h3&gt;
  
  
  Links
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;YINI homepage: &lt;a href="https://yini-lang.org" rel="noopener noreferrer"&gt;https://yini-lang.org&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;YINI on GitHub: &lt;a href="https://github.com/YINI-lang" rel="noopener noreferrer"&gt;https://github.com/YINI-lang&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Specification: &lt;a href="https://yini-lang.org/specification" rel="noopener noreferrer"&gt;https://yini-lang.org/specification&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;CLI tool: &lt;a href="https://yini-lang.org/tools/yini-cli" rel="noopener noreferrer"&gt;https://yini-lang.org/tools/yini-cli&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;TypeScript parser: &lt;a href="https://yini-lang.org/tools/yini-parser-ts" rel="noopener noreferrer"&gt;https://yini-lang.org/tools/yini-parser-ts&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Python parser: &lt;a href="https://yini-lang.org/tools/yini-parser-python" rel="noopener noreferrer"&gt;https://yini-lang.org/tools/yini-parser-python&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;




&lt;h3&gt;
  
  
  Feedback welcome
&lt;/h3&gt;

&lt;p&gt;RC 6 is a release-candidate specification, so feedback is still useful.&lt;/p&gt;

&lt;p&gt;Especially helpful feedback includes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Confusing syntax rules.&lt;/li&gt;
&lt;li&gt;Parser edge cases.&lt;/li&gt;
&lt;li&gt;Unclear examples.&lt;/li&gt;
&lt;li&gt;Places where strict and lenient behavior should be clearer.&lt;/li&gt;
&lt;li&gt;Documentation gaps.&lt;/li&gt;
&lt;li&gt;And real-world configuration examples that would be useful to test against.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you try YINI, find a rough edge, or have opinions about configuration formats, I would be happy to hear them.&lt;/p&gt;

</description>
      <category>tooling</category>
      <category>opensource</category>
      <category>javascript</category>
      <category>python</category>
    </item>
    <item>
      <title>YINI parser for Python is now released ✨️</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Sat, 13 Jun 2026 19:43:28 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-parser-python-is-now-public-feedback-and-early-testing-welcome-2985</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-parser-python-is-now-public-feedback-and-early-testing-welcome-2985</guid>
      <description>&lt;h2&gt;
  
  
  yini-parser-python is now public - feedback and early testing welcome
&lt;/h2&gt;

&lt;p&gt;I recently made &lt;a href="https://github.com/YINI-lang/yini-parser-python" rel="noopener noreferrer"&gt;yini-parser-python&lt;/a&gt; public.&lt;/p&gt;

&lt;p&gt;It is a Python parser for &lt;a href="https://yini-lang.org" rel="noopener noreferrer"&gt;YINI&lt;/a&gt; - an INI-inspired, indentation-insensitive configuration format with explicit nested sections and predictable parsing rules.&lt;/p&gt;

&lt;p&gt;The package is also on PyPI: &lt;a href="https://pypi.org/project/yini-parser/" rel="noopener noreferrer"&gt;pypi.org/project/yini-parser&lt;/a&gt;&lt;/p&gt;




&lt;p&gt;YINI is still a young project and the spec is moving toward its first stable &lt;code&gt;1.0.0&lt;/code&gt; release. That is exactly why I want feedback now - before things solidify. If something looks unclear, surprising, fragile, or difficult to maintain, I would rather hear about it at this stage than after the format is locked.&lt;/p&gt;

&lt;h3&gt;
  
  
  What the parser does
&lt;/h3&gt;

&lt;p&gt;The goal of &lt;code&gt;yini-parser-python&lt;/code&gt; is to provide a usable Python implementation of YINI. A small example looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight ini"&gt;&lt;code&gt;&lt;span class="err"&gt;@yini&lt;/span&gt;

&lt;span class="err"&gt;^&lt;/span&gt; &lt;span class="err"&gt;Application&lt;/span&gt;
&lt;span class="py"&gt;name&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;'Demo Application'&lt;/span&gt;
&lt;span class="py"&gt;version&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;'1.0.0'&lt;/span&gt;
&lt;span class="py"&gt;debug&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;yes&lt;/span&gt;

&lt;span class="err"&gt;^^&lt;/span&gt; &lt;span class="err"&gt;Server&lt;/span&gt;
&lt;span class="py"&gt;host&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;'localhost'&lt;/span&gt;
&lt;span class="py"&gt;port&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;8080&lt;/span&gt;

&lt;span class="err"&gt;^^^&lt;/span&gt; &lt;span class="err"&gt;Logging&lt;/span&gt;
&lt;span class="py"&gt;level&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;'info'&lt;/span&gt;
&lt;span class="py"&gt;file&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s"&gt;'./app.log'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Which represents this structure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Application
└─ Server
   └─ Logging
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Section nesting is defined by the markers - not by indentation or whitespace. That is the core idea.&lt;/p&gt;

&lt;h3&gt;
  
  
  Current status
&lt;/h3&gt;

&lt;p&gt;The parser is early-stage but usable enough for testing and review. It currently passes the full &lt;code&gt;yini-test&lt;/code&gt; suite - a separate Python-based test project with golden tests for parser behavior.&lt;/p&gt;

&lt;p&gt;That suite has around 150 tests at the moment (76 lenient + 75 strict = 151 golden tests, I might make a more specific post about yini-test later on). It covers the important cases but is not yet comprehensive. More tests will be added as both the format and the implementations mature. The &lt;code&gt;yini-test&lt;/code&gt; project is also planned to go public, if it has not already by the time you read this.&lt;/p&gt;

&lt;h3&gt;
  
  
  What kind of feedback would be useful?
&lt;/h3&gt;

&lt;p&gt;Primarily:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Parser bugs&lt;/li&gt;
&lt;li&gt;Unclear or surprising behavior&lt;/li&gt;
&lt;li&gt;Edge cases worth adding to the test suite&lt;/li&gt;
&lt;li&gt;Packaging or installation issues&lt;/li&gt;
&lt;li&gt;Python API design&lt;/li&gt;
&lt;li&gt;Documentation improvements&lt;/li&gt;
&lt;li&gt;Places where the implementation could be simpler or more maintainable&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Bug reports, small reproductions, pull requests, and implementation suggestions are all welcome. Alpha or beta testers too - even a quick "I tried this and it worked / did not work" is useful right now.&lt;/p&gt;

&lt;h3&gt;
  
  
  Why share it before 1.0.0?
&lt;/h3&gt;

&lt;p&gt;Because this is when careful review matters most. Once a configuration format stabilizes, small syntax and behavior decisions become much harder to change. I would rather get practical feedback early - especially from developers with experience in configuration formats, parsers, tooling, or Python packaging.&lt;/p&gt;

&lt;p&gt;YINI is not trying to replace JSON, YAML, TOML, or INI. Those all have valid use cases. This is a more focused experiment:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;What if INI-style configuration had clearer nested structure, while staying readable and predictable?&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;That is the design space I am trying to test.&lt;/p&gt;

&lt;h3&gt;
  
  
  Links
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;GitHub: &lt;a href="https://github.com/YINI-lang/yini-parser-python" rel="noopener noreferrer"&gt;YINI-lang/yini-parser-python&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;PyPI: &lt;a href="https://pypi.org/project/yini-parser/" rel="noopener noreferrer"&gt;pypi.org/project/yini-parser&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Organization: &lt;a href="https://github.com/YINI-lang" rel="noopener noreferrer"&gt;github.com/YINI-lang&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Website: &lt;a href="https://yini-lang.org" rel="noopener noreferrer"&gt;yini-lang.org&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you try the parser and notice anything odd, unclear, or broken - feel free to make an issue, comment, or pull request, that would be very much appreciated.&lt;/p&gt;

&lt;p&gt;Thanks for reading,&lt;br&gt;&lt;br&gt;
Marko&lt;/p&gt;

</description>
      <category>python</category>
      <category>opensource</category>
      <category>programming</category>
      <category>tooling</category>
    </item>
    <item>
      <title>YINI (config format) RC.5 and yini-parser 1.5.0: making configuration stricter, clearer, and easier to trust</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Thu, 09 Apr 2026 21:48:41 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-config-format-rc5-and-yini-parser-150-making-configuration-stricter-clearer-and-easier-29na</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-config-format-rc5-and-yini-parser-150-making-configuration-stricter-clearer-and-easier-29na</guid>
      <description>&lt;h1&gt;
  
  
  YINI RC.5 and yini-parser 1.5.0: making configuration stricter, clearer, and easier to trust
&lt;/h1&gt;

&lt;p&gt;I have been working for quite a while on &lt;strong&gt;YINI&lt;/strong&gt;, a configuration format that tries to sit somewhere between &lt;strong&gt;INI&lt;/strong&gt;, &lt;strong&gt;JSON&lt;/strong&gt;, and &lt;strong&gt;YAML&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;The original idea was simple: I wanted something that stayed pleasant to read and edit by hand, but was still structured enough to handle real-world configuration without feeling vague or fragile.&lt;/p&gt;

&lt;p&gt;Over time, that idea turned into a full specification, parser work, CLI tooling, examples, grammar files, and a growing list of design decisions that needed to become clearer and more consistent.&lt;/p&gt;

&lt;p&gt;This month was one of those milestones where several pieces moved forward together:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;the &lt;strong&gt;YINI Specification&lt;/strong&gt; reached &lt;strong&gt;v1.0.0-RC.5&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;the official &lt;strong&gt;Node.js / TypeScript parser&lt;/strong&gt; reached &lt;strong&gt;v1.5.0&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A lot of this update was not about flashy new syntax.&lt;br&gt;&lt;br&gt;
It was about making the format more precise, the parser more consistent, and strict mode more trustworthy.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TL;DR&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;YINI Spec reached &lt;strong&gt;v1.0.0-RC.5&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;yini-parser&lt;/code&gt; reached &lt;strong&gt;v1.5.0&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;strict mode now requires &lt;code&gt;/END&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;strict mode now requires exactly one explicit top-level section&lt;/li&gt;
&lt;li&gt;parser, grammar, examples, and tests were all brought into closer alignment&lt;/li&gt;
&lt;/ul&gt;


&lt;h2&gt;
  
  
  What YINI aims to be
&lt;/h2&gt;

&lt;p&gt;YINI is a human-readable configuration format with:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;explicit sections and nested sections&lt;/li&gt;
&lt;li&gt;comments&lt;/li&gt;
&lt;li&gt;strings, numbers, booleans, null, lists, and inline objects&lt;/li&gt;
&lt;li&gt;predictable parsing rules&lt;/li&gt;
&lt;li&gt;optional lenient and strict modes&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A very small example looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
name = "My App"
debug = false

    ^^ Features
    caching = on
    telemetry = off
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The idea is to keep structure visible, without relying on indentation as syntax.&lt;/p&gt;

&lt;h2&gt;
  
  
  What changed in RC.5
&lt;/h2&gt;

&lt;p&gt;The specification changes in &lt;strong&gt;YINI v1.0.0-RC.5&lt;/strong&gt; were mostly about tightening rules and reducing ambiguity.&lt;/p&gt;




&lt;h2&gt;
  
  
  1. &lt;code&gt;/END&lt;/code&gt; is now required in strict mode
&lt;/h2&gt;

&lt;p&gt;This is probably the biggest change.&lt;/p&gt;

&lt;p&gt;The document terminator &lt;code&gt;/END&lt;/code&gt; is now:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;required in strict mode&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;optional in lenient mode&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That may sound like a small detail, but it changes the contract of strict mode in an important way.&lt;/p&gt;

&lt;p&gt;Before, a strict document could simply end at EOF.&lt;br&gt;
Now, in strict mode, the document must explicitly declare that it is complete.&lt;/p&gt;

&lt;p&gt;That helps in situations where configuration is:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;copied only partly&lt;/li&gt;
&lt;li&gt;truncated&lt;/li&gt;
&lt;li&gt;transferred incompletely&lt;/li&gt;
&lt;li&gt;cut off during file copy&lt;/li&gt;
&lt;li&gt;broken during manual copy-and-paste&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In other words, strict mode now becomes better at rejecting incomplete documents instead of quietly assuming they ended correctly.&lt;/p&gt;

&lt;p&gt;A strict document now looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
name = "My App"
debug = false
/END
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That explicit ending felt like the right fit for a mode whose purpose is stricter validation.&lt;/p&gt;




&lt;h2&gt;
  
  
  2. Strict mode now clearly requires exactly one top-level section
&lt;/h2&gt;

&lt;p&gt;Another important clarification was around top-level structure.&lt;/p&gt;

&lt;p&gt;In &lt;strong&gt;lenient mode&lt;/strong&gt;, orphan members can still exist at the root level, or be exposed under an implicit &lt;code&gt;base&lt;/code&gt;, depending on implementation choices.&lt;/p&gt;

&lt;p&gt;In &lt;strong&gt;strict mode&lt;/strong&gt;, that is no longer just a loose expectation. The rule is now much clearer:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;there must be &lt;strong&gt;exactly one explicit top-level section&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;top-level orphan members are not allowed&lt;/li&gt;
&lt;li&gt;additional sections must be nested under that single root section&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This makes strict mode easier to reason about and easier to validate.&lt;/p&gt;




&lt;h2&gt;
  
  
  3. Section header spacing rules were clarified
&lt;/h2&gt;

&lt;p&gt;YINI section headers support both repeated markers and numeric shorthand.&lt;/p&gt;

&lt;p&gt;Examples:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
^^ Features
^7 DeepSection
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;RC.5 clarifies that:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;repeated/basic section headers do &lt;strong&gt;not&lt;/strong&gt; require a space before the name&lt;/li&gt;
&lt;li&gt;numeric shorthand headers do require a space after the number
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^App
^^Features
^7 DeepSection
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But shorthand like this is not:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^7DeepSection
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This was partly about grammar clarity, and partly about parser consistency.&lt;/p&gt;




&lt;h2&gt;
  
  
  4. Colon-based lists were fully removed from samples and examples
&lt;/h2&gt;

&lt;p&gt;Colon-based lists had already been dropped earlier as a supported feature, but RC.5 cleaned this up fully across samples and examples.&lt;/p&gt;

&lt;p&gt;So now the examples consistently use bracketed lists:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;items = ["a", "b", "c"]
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;instead of older colon-list forms.&lt;/p&gt;

&lt;p&gt;This is one of those changes that makes the format feel a bit less over-engineered and more coherent: less syntax surface, fewer edge cases, and less mental overhead.&lt;br&gt;
Less syntax surface, fewer edge cases, less mental overhead.&lt;/p&gt;




&lt;h2&gt;
  
  
  5. The ANTLR4 grammar files were cleaned up
&lt;/h2&gt;

&lt;p&gt;This was a quieter update, but a satisfying one.&lt;/p&gt;

&lt;p&gt;The lexer and parser &lt;code&gt;.g4&lt;/code&gt; files were cleaned up and reorganized to make them:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;easier to read&lt;/li&gt;
&lt;li&gt;easier to maintain&lt;/li&gt;
&lt;li&gt;more internally consistent&lt;/li&gt;
&lt;li&gt;easier to keep aligned with the specification&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That kind of work is not always visible from the outside, but it matters when the format is meant to have a real grammar rather than just an informal idea of how parsing should work.&lt;/p&gt;




&lt;h2&gt;
  
  
  What changed in yini-parser 1.5.0
&lt;/h2&gt;

&lt;p&gt;On the implementation side, &lt;strong&gt;yini-parser v1.5.0&lt;/strong&gt; brings the Node.js / TypeScript parser in line with the RC.5 specification.&lt;/p&gt;

&lt;h3&gt;
  
  
  Strict mode behavior now matches the spec more closely
&lt;/h3&gt;

&lt;p&gt;The parser now enforces that strict mode:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;requires &lt;code&gt;/END&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;requires exactly one explicit top-level section&lt;/li&gt;
&lt;li&gt;applies the clarified section-header spacing rules&lt;/li&gt;
&lt;li&gt;performs stricter checks around top-level structure&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That means the behavior is now more predictable, and closer to what the specification actually says.&lt;/p&gt;

&lt;h3&gt;
  
  
  Lenient mode handling was refined
&lt;/h3&gt;

&lt;p&gt;The parser also got better around the softer side of the format:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;members outside explicit sections are handled more clearly in lenient mode&lt;/li&gt;
&lt;li&gt;empty values and explicit null handling were clarified and tightened&lt;/li&gt;
&lt;li&gt;top-level structural behavior is now easier to reason about in both modes&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This matters because lenient mode is supposed to be forgiving, but still consistent.&lt;/p&gt;

&lt;h3&gt;
  
  
  Error handling and &lt;code&gt;throwOnError&lt;/code&gt; were improved
&lt;/h3&gt;

&lt;p&gt;A smaller but useful implementation fix was around error handling:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;throwOnError&lt;/code&gt; option detection was fixed&lt;/li&gt;
&lt;li&gt;public parameter names and related documentation were cleaned up&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;throwOnError&lt;/code&gt; now works more consistently together with the selected fail level&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;These are the kinds of details that make parser APIs much less frustrating to use in real tooling.&lt;/p&gt;

&lt;h3&gt;
  
  
  Validation and test coverage expanded
&lt;/h3&gt;

&lt;p&gt;This release also expanded validation and tests around:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;section headers&lt;/li&gt;
&lt;li&gt;shorthand markers&lt;/li&gt;
&lt;li&gt;backticked names&lt;/li&gt;
&lt;li&gt;invalid dotted section names&lt;/li&gt;
&lt;li&gt;error recovery&lt;/li&gt;
&lt;li&gt;null handling&lt;/li&gt;
&lt;li&gt;fixture parsing&lt;/li&gt;
&lt;li&gt;smoke and integration coverage&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A new large smoke/golden fixture was also added and validated:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;code&gt;c-industrial-monitoring-and-automation-platform.smoke.yini&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;And some previously skipped smoke tests were fixed and re-enabled as well.&lt;/p&gt;

&lt;p&gt;That part makes me especially happy, because parser work is only as trustworthy as the tests around it.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why these changes matter
&lt;/h2&gt;

&lt;p&gt;None of this is about making YINI more complicated for the sake of it.&lt;/p&gt;

&lt;p&gt;It is more about giving each mode a clearer purpose.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Lenient mode&lt;/strong&gt; should remain practical for human-edited configuration.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Strict mode&lt;/strong&gt; should be something you can trust in:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;validation-heavy environments&lt;/li&gt;
&lt;li&gt;CI&lt;/li&gt;
&lt;li&gt;generated configuration&lt;/li&gt;
&lt;li&gt;tooling&lt;/li&gt;
&lt;li&gt;cases where incomplete or malformed input should fail fast&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Requiring &lt;code&gt;/END&lt;/code&gt; in strict mode, requiring exactly one top-level section, and tightening the parser around these rules all move in that direction.&lt;/p&gt;

&lt;h2&gt;
  
  
  Example: why strict &lt;code&gt;/END&lt;/code&gt; helps
&lt;/h2&gt;

&lt;p&gt;A document that just stops at EOF can look complete even when it is not.&lt;/p&gt;

&lt;p&gt;A document that ends with &lt;code&gt;/END&lt;/code&gt; is making a stronger statement:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;this is the intended end of the document&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;That becomes useful when files are:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;partially copied&lt;/li&gt;
&lt;li&gt;manually pasted&lt;/li&gt;
&lt;li&gt;embedded into another system&lt;/li&gt;
&lt;li&gt;transferred incompletely&lt;/li&gt;
&lt;li&gt;edited in the wrong place and saved in broken form&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That is one of the main reasons I ended up feeling that strict mode should require it.&lt;/p&gt;

&lt;h3&gt;
  
  
  Example
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// Lenient mode may allow:

name = "My App"

^ App
debug = true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// Strict mode requires:

^ App
name = "My App"
debug = true

/END
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  Current direction
&lt;/h2&gt;

&lt;p&gt;YINI is getting close to the point where the core shape of the format feels stable.&lt;/p&gt;

&lt;p&gt;There is still work to do, of course, but RC.5 and parser 1.5.0 feel like an important step because they strengthen the relationship between:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;the specification&lt;/li&gt;
&lt;li&gt;the grammar&lt;/li&gt;
&lt;li&gt;the parser behavior&lt;/li&gt;
&lt;li&gt;the examples&lt;/li&gt;
&lt;li&gt;the tests&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That kind of alignment is not glamorous, but it is the kind of thing that makes a format feel real.&lt;/p&gt;

&lt;h2&gt;
  
  
  If this kind of thing interests you
&lt;/h2&gt;

&lt;p&gt;If you work with:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;configuration-heavy tools&lt;/li&gt;
&lt;li&gt;parser development&lt;/li&gt;
&lt;li&gt;DSLs&lt;/li&gt;
&lt;li&gt;TypeScript tooling&lt;/li&gt;
&lt;li&gt;or just enjoy format design&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I would genuinely be interested in how others think about strict vs lenient parsing, explicit document termination, and where a config format should draw the line between convenience and validation.&lt;/p&gt;

&lt;h2&gt;
  
  
  Links
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://yini-lang.org?utm_source=devto&amp;amp;utm_medium=social&amp;amp;utm_campaign=rc5_release&amp;amp;utm_content=post" rel="noopener noreferrer"&gt;YINI homepage&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/YINI-lang" rel="noopener noreferrer"&gt;YINI on GitHub&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Thanks for reading.&lt;/p&gt;

</description>
      <category>opensource</category>
      <category>node</category>
      <category>tooling</category>
      <category>typescript</category>
    </item>
    <item>
      <title>YINI CLI 1.2.1-beta: Safer Validation, Improved Help, and Smarter Output Handling</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Mon, 23 Feb 2026 19:00:31 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-cli-121-beta-safer-validation-improved-help-nd-smarter-output-handling-2nkk</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-cli-121-beta-safer-validation-improved-help-nd-smarter-output-handling-2nkk</guid>
      <description>&lt;p&gt;This release improves validation robustness in &lt;code&gt;yini-cli&lt;/code&gt; and makes CLI behavior more predictable and consistent.&lt;/p&gt;




&lt;h2&gt;
  
  
  1.2.1-beta — 2026-02
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Improved
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;validate&lt;/code&gt; command:

&lt;ul&gt;
&lt;li&gt;Strengthened diagnostics handling and metadata safety checks.&lt;/li&gt;
&lt;li&gt;Replaced unsafe internal assertions with controlled error handling.&lt;/li&gt;
&lt;li&gt;Improved &lt;code&gt;--silent&lt;/code&gt; behavior and exit code consistency.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  1.2.0-beta — 2026-02
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Improved
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;--help&lt;/code&gt; now displays full help for all commands.
Command-specific help remains available via:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  yini &lt;span class="nb"&gt;help&lt;/span&gt; &amp;lt;&lt;span class="nb"&gt;command&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Changed
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Extended environment information is now available via the &lt;code&gt;info&lt;/code&gt; command.
The global &lt;code&gt;--info&lt;/code&gt; option has been removed. Use:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;  yini info
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;parse&lt;/code&gt; now defaults to formatted JSON output.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;--compact&lt;/code&gt; outputs minified JSON (no whitespace).&lt;/li&gt;
&lt;li&gt;Improved &lt;code&gt;--output&lt;/code&gt; file handling:

&lt;ul&gt;
&lt;li&gt;Output is written only if the destination file does not exist or is older than the source &lt;code&gt;.yini&lt;/code&gt; file.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;--overwrite&lt;/code&gt; always replaces existing files.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;--no-overwrite&lt;/code&gt; prevents replacing existing files.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Added
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;--js&lt;/code&gt; option for &lt;code&gt;parse&lt;/code&gt; to output JavaScript-style objects.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Deprecated
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;--pretty&lt;/code&gt; flag for &lt;code&gt;parse&lt;/code&gt; (use &lt;code&gt;--json&lt;/code&gt; explicitly if needed).&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  Try YINI CLI
&lt;/h2&gt;

&lt;p&gt;Install globally:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; yini-cli
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or run without installing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx yini-cli &lt;span class="nt"&gt;--help&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  Explore the Project
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;GitHub: &lt;a href="https://github.com/YINI-lang/yini-cli" rel="noopener noreferrer"&gt;https://github.com/YINI-lang/yini-cli&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;npm: &lt;a href="https://www.npmjs.com/package/yini-cli" rel="noopener noreferrer"&gt;https://www.npmjs.com/package/yini-cli&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Documentation &amp;amp; format specification: &lt;a href="https://yini-lang.org?utm_source=devto&amp;amp;utm_medium=post&amp;amp;utm_campaign=yini_cli_release_1_2_x" rel="noopener noreferrer"&gt;YINI homepage&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>node</category>
      <category>cli</category>
      <category>opensource</category>
      <category>tooling</category>
    </item>
    <item>
      <title>I spent a week working on regression tests &amp; metadata guarantees on the YINI config/settings parser</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Wed, 31 Dec 2025 01:09:58 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/i-spent-a-week-working-on-regression-tests-metadata-guarantees-on-the-yini-configsettings-parser-5f2m</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/i-spent-a-week-working-on-regression-tests-metadata-guarantees-on-the-yini-configsettings-parser-5f2m</guid>
      <description>&lt;p&gt;Hey 👋&lt;/p&gt;

&lt;p&gt;I just wanted to share a small win from my side project.&lt;/p&gt;

&lt;p&gt;I've been working on something called YINI for a while now - it's a configuration format together with a TypeScript parser (with spec, grammar, etc).&lt;br&gt;
The goal is basically to be a calmer middle ground between INI, JSON, and YAML for larger, real-world configuration files.&lt;/p&gt;

&lt;p&gt;This past week I didn't really add any new features.&lt;br&gt;
Instead, I finally sat down and did something I've been postponing for a long time: making the parser really solid.&lt;/p&gt;

&lt;p&gt;I just shipped v1.3.3-beta, and most of the work went into building proper smoke and regression tests around the parser.&lt;br&gt;
Not glamorous work at all - but it feels incredibly good now that it's in place.&lt;/p&gt;

&lt;p&gt;The new tests parse a couple of large production-style configurations (one corporate SaaS setup and one more high-security / distributed setup) and verify that:&lt;/p&gt;

&lt;p&gt;the output is identical in default mode, strict mode, and strict+metadata mode&lt;/p&gt;

&lt;p&gt;metadata and diagnostics behave correctly for both valid and broken inputs&lt;/p&gt;

&lt;p&gt;The API didn't change at all in this release - it's simply about making the project more predictable, safer to depend on, and easier to evolve.&lt;/p&gt;

&lt;p&gt;It took longer than I expected, but I'm genuinely happy with where it landed.&lt;/p&gt;

&lt;p&gt;This release was also important to get out because I'm using this parser as the foundation for the next big step of the project: expanding and refactoring the YINI CLI to make it more robust and production-ready.&lt;/p&gt;

&lt;p&gt;If you're building developer tools, working with config-heavy systems, or just dealing with a lot of INI/JSON/XML files in general, you might find YINI interesting:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;https://github.com/YINI-lang/yini-parser-typescript&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I'd really appreciate any real-world testing or feedback. And good luck with your own side projects, they always end up being a lot more work than they first appear.&lt;/p&gt;

&lt;p&gt;Thanks for reading.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;&lt;/p&gt;

</description>
      <category>sideprojects</category>
      <category>opensource</category>
      <category>node</category>
      <category>programming</category>
    </item>
    <item>
      <title>🔧 yini-cli v1.1.1-beta released</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Sat, 20 Dec 2025 22:52:18 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-cli-v111-beta-released-488f</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-cli-v111-beta-released-488f</guid>
      <description>&lt;p&gt;A new &lt;strong&gt;beta release&lt;/strong&gt; of &lt;code&gt;yini-cli&lt;/code&gt;, the command-line tool for working with YINI configuration files, is now available.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's new in v1.1.1-beta
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Updated: The CLI now uses YINI Parser &lt;code&gt;v1.3.2-beta&lt;/code&gt; (previously &lt;code&gt;v1.3.0-beta&lt;/code&gt;).&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This brings in:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;UTF-8 BOM handling (with and without BOM).&lt;/li&gt;
&lt;li&gt;Shebang (#!) support (the line will be skipped if detected, without breaking parsing).&lt;/li&gt;
&lt;li&gt;Additional parser robustness and test coverage.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  About YINI
&lt;/h2&gt;

&lt;p&gt;YINI is an &lt;strong&gt;INI-inspired configuration format&lt;/strong&gt; designed for clarity and predictable behavior.&lt;br&gt;
It supports nesting, comments, and a formally defined syntax, while remaining easy to read and edit by hand.&lt;/p&gt;

&lt;h2&gt;
  
  
  Links
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;📦 npm: &lt;a href="https://www.npmjs.com/package/yini-cli" rel="noopener noreferrer"&gt;https://www.npmjs.com/package/yini-cli&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;🧠 &lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;💻 Source code: &lt;a href="https://github.com/YINI-lang/yini-cli" rel="noopener noreferrer"&gt;https://github.com/YINI-lang/yini-cli&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Feedback and small improvements are always welcome.&lt;br&gt;
No breaking CLI changes were introduced.&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>cli</category>
      <category>node</category>
      <category>tooling</category>
    </item>
    <item>
      <title>YINI Config Parser v1.3.2-beta Released (Node.js)</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Tue, 16 Dec 2025 20:46:37 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-config-parser-v132-beta-released-nodejs-kcg</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-config-parser-v132-beta-released-nodejs-kcg</guid>
      <description>&lt;p&gt;A new beta of the official TypeScript parser for YINI is out!&lt;br&gt;
This release focuses on real-world usability, robust file handling, and dependency hygiene.&lt;/p&gt;

&lt;p&gt;If you're new to YINI: it's a modern, human-friendly configuration format that aims to keep INI-style readability while supporting real structure.&lt;/p&gt;

&lt;h2&gt;
  
  
  What's new in 1.3.2-beta
&lt;/h2&gt;

&lt;h3&gt;
  
  
  UTF-8 BOM support
&lt;/h3&gt;

&lt;p&gt;YINI now correctly handles UTF-8 files with or without a Byte Order Mark (BOM).&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Safe stripping of a leading BOM (U+FEFF)&lt;/li&gt;
&lt;li&gt;Identical parsing behavior for:

&lt;ul&gt;
&lt;li&gt;UTF-8 without BOM&lt;/li&gt;
&lt;li&gt;UTF-8 with BOM&lt;/li&gt;
&lt;li&gt;BOM followed by a blank line&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Explicitly does not treat mid-file U+FEFF as a BOM&lt;/li&gt;
&lt;li&gt;Comprehensive test fixtures added for all cases&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This makes YINI more robust when consuming files created by different editors, platforms, and tooling.&lt;/p&gt;

&lt;h3&gt;
  
  
  Shebang (#!) support
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;YINI files can now start with a shebang line, which is ignored by the parser.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Dependency updates &amp;amp; security hygiene
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;All project dependencies (~14) updated to their latest versions&lt;/li&gt;
&lt;li&gt;Includes TypeScript and packages with reported security advisories&lt;/li&gt;
&lt;li&gt;Node.js type definitions intentionally left unchanged&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;No breaking API changes were introduced.&lt;/p&gt;

&lt;h2&gt;
  
  
  📦 Installation
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;npm install yini-parser
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Or, if you're already using it, just bump to 1.3.2-beta.&lt;/p&gt;

&lt;h2&gt;
  
  
  Links
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Source code: &lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;https://github.com/YINI-lang/yini-parser-typescript&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;npm: &lt;a href="https://www.npmjs.com/package/yini-parser" rel="noopener noreferrer"&gt;https://www.npmjs.com/package/yini-parser&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Specification &amp;amp; docs: &lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Feedback welcome
&lt;/h2&gt;

&lt;p&gt;YINI is still evolving, and feedback from real users is invaluable.&lt;br&gt;
If you try this release and run into anything odd, or have thoughts on the format itself, feel free to open an issue or start a discussion.&lt;/p&gt;

&lt;p&gt;Thanks to everyone following and testing the project 🙌&lt;br&gt;
Thanks to everyone following and testing the project 🙌&lt;/p&gt;

</description>
      <category>node</category>
      <category>typescript</category>
      <category>tooling</category>
    </item>
    <item>
      <title>The New YINI Homepage Is Live — A Modern, Human-Friendly Config Format</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Sun, 09 Nov 2025 02:20:41 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/the-yini-homepage-is-live-a-modern-human-friendly-config-format-28al</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/the-yini-homepage-is-live-a-modern-human-friendly-config-format-28al</guid>
      <description>&lt;p&gt;Hey everyone 👋&lt;/p&gt;

&lt;p&gt;I'm excited to share that the new homepage for &lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=social&amp;amp;utm_campaign=rc5_release&amp;amp;utm_content=post" rel="noopener noreferrer"&gt;YINI config format↗&lt;/a&gt; is now live!&lt;br&gt;&lt;br&gt;
YINI is a &lt;strong&gt;modern, structured, human-friendly configuration&lt;/strong&gt; format that tries to bring together the simplicity of INI with the flexibility of YAML.&lt;/p&gt;

&lt;h2&gt;
  
  
  🧩 What Is YINI?
&lt;/h2&gt;

&lt;p&gt;YINI was designed to make configuration files both readable for humans and consistent for machines.&lt;/p&gt;

&lt;p&gt;It takes inspiration from INI, YAML, and JSON — but simplifies the rules while still supporting modern features like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Nested sections using clear markers (&lt;code&gt;^&lt;/code&gt;, &lt;code&gt;^^&lt;/code&gt;, etc.)&lt;/li&gt;
&lt;li&gt;Arrays &lt;code&gt;[1, 2, 3]&lt;/code&gt; and objects &lt;code&gt;{ key: "value" }&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;Inline and full-line comments&lt;/li&gt;
&lt;li&gt;Strict and lenient parsing modes
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
name = "Demo"
features = ["search", "dark-mode"]

^^ Server
host = "0.0.0.0"
port = 8080
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  🌐 The New Homepage
&lt;/h2&gt;

&lt;p&gt;The new site — &lt;a href="https://yini-lang.org/" rel="noopener noreferrer"&gt;yini-lang.org ↗&lt;/a&gt; — brings everything together:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;🧭 Get Started guide&lt;/li&gt;
&lt;li&gt;⚙️ Quick Tutorial with examples&lt;/li&gt;
&lt;li&gt;📘 Full Specification&lt;/li&gt;
&lt;li&gt;💡 FAQ and explanations&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;It's built with Astro + Tailwind, and designed to be fast, clean, and accessible — the perfect home for YINI as the ecosystem continues to grow.&lt;/p&gt;

&lt;h2&gt;
  
  
  📦 The YINI Ecosystem
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;yini-parser-typescript&lt;/code&gt; — the official TypeScript parser library&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;yini-cli&lt;/code&gt; — a simple CLI for parsing, validating, and converting YINI files&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Specification&lt;/strong&gt; — now at v1.0 RC stage, aligning parser behavior with the spec&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Both projects are open-source on GitHub under &lt;a href="https://github.com/YINI-lang" rel="noopener noreferrer"&gt;@YINI-lang ↗&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  🗣️ Feedback Welcome
&lt;/h2&gt;

&lt;p&gt;This is still early days for YINI, and community feedback is incredibly valuable.&lt;br&gt;
If you’d like to try it out, explore the homepage, or contribute ideas, you’re more than welcome!&lt;br&gt;
👉 &lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;&lt;br&gt;
👉 &lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;Check the parser on GitHub → yini-parser-typescript&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Thanks for reading — and for helping shape a cleaner, more predictable future for config files 💡&lt;/p&gt;

&lt;p&gt;— Marko Seppänen&lt;/p&gt;

</description>
      <category>config</category>
      <category>programming</category>
      <category>webdev</category>
      <category>opensource</category>
    </item>
    <item>
      <title>🚀 YINI Parser v1.3.0-beta – Smarter Options, Safer Metadata, and New Controls</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Tue, 23 Sep 2025 14:20:52 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-parser-v130-beta-smarter-options-safer-metadata-and-new-controls-2gn0</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-parser-v130-beta-smarter-options-safer-metadata-and-new-controls-2gn0</guid>
      <description>&lt;p&gt;I've just released yini-parser v1.3.0-beta 🎉 (Node package) - a big step forward for ergonomics, diagnostics, and developer experience when working with &lt;a href="https://github.com/YINI-lang/YINI-spec" rel="noopener noreferrer"&gt;YINI configuration format&lt;/a&gt;, the human-friendly configuration format inspired by INI but with modern clarity.&lt;/p&gt;

&lt;p&gt;This release focuses on &lt;strong&gt;cleaner public APIs&lt;/strong&gt;, &lt;strong&gt;new output controls&lt;/strong&gt;, and &lt;strong&gt;better tooling&lt;/strong&gt; around metadata and CI.&lt;/p&gt;

&lt;h2&gt;
  
  
  ✨ What's New
&lt;/h2&gt;

&lt;h3&gt;
  
  
  🐛 Fixed
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Fixed a bug where &lt;code&gt;buildResultMetadata(..)&lt;/code&gt; could occasionally produce an &lt;code&gt;undefined&lt;/code&gt; error.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  🔄 Renamed (Breaking API Changes)
&lt;/h3&gt;

&lt;p&gt;To make public types more ergonomic for end-users, several interfaces were renamed:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;AllUserOptions&lt;/code&gt; → &lt;code&gt;ParseOptions&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;PrimaryUserParams&lt;/code&gt; → &lt;code&gt;BasicOptions&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;OnDuplicateKey&lt;/code&gt; → &lt;code&gt;DuplicateKeyPolicy&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This makes names shorter, more consistent, and closer to their intent.&lt;/p&gt;

&lt;h3&gt;
  
  
  📖 Clarified
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;The &lt;code&gt;strictMode&lt;/code&gt; parameter in TSDoc has been clarified:
It defines the baseline ruleset (&lt;code&gt;true&lt;/code&gt; = strict, &lt;code&gt;false&lt;/code&gt; = lenient).
Rule-specific options (e.g., &lt;code&gt;treatEmptyValueAsNull&lt;/code&gt;, &lt;code&gt;onDuplicateKey&lt;/code&gt;) may override the baseline.
When overrides are applied, the effective mode becomes &lt;strong&gt;custom&lt;/strong&gt;.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  🆕 New Features
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;DocumentTerminatorRule and EmptyValueRule: new user-facing parsing rule value types.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;quiet&lt;/code&gt; option:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Only prints errors to the console.&lt;/li&gt;
&lt;li&gt;Warnings, notices, etc. are suppressed.&lt;/li&gt;
&lt;li&gt;Diagnostics are still captured in metadata.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;silent&lt;/code&gt; option:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Suppresses all console output, even errors.&lt;/li&gt;
&lt;li&gt;Programmatic callers should use metadata; CLI users should rely on the exit code.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;throwOnError&lt;/code&gt; option:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;true&lt;/code&gt; (default): parser throws on parse errors.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;false&lt;/code&gt;: errors are reported via diagnostics without throwing.&lt;/li&gt;
&lt;li&gt;⚠️ Planned change: next release will switch the default to false.&lt;/li&gt;
&lt;li&gt;✅ Action: set &lt;code&gt;throwOnError: true&lt;/code&gt; to keep current behavior, or &lt;code&gt;throwOnError: false&lt;/code&gt; to adopt the upcoming behavior.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  📊 Metadata Improvements
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Added effectiveMode inside meta.diagnostics.effectiveOptions.&lt;/li&gt;
&lt;li&gt;Metadata bumped to v1.1.1.&lt;/li&gt;
&lt;li&gt;Fields strictMode and effectiveOptions now correctly reflect when rules override the initial mode.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The resultet metadata looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;meta&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;parserVersion&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;1.3.0-beta&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;mode&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;strict&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;totalErrors&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;totalWarnings&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;totalMessages&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;runStartedAt&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;2025-09-23T14:23:22.587Z&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;runFinishedAt&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;2025-09-23T14:23:22.618Z&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;durationMs&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mf"&gt;30.746&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;preservesOrder&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;orderGuarantee&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;implementation-defined&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;source&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;sourceType&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;inline&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;hasDocumentTerminator&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;hasYiniMarker&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;lineCount&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;byteSize&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;sha256&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;d79db628387ad8244fc3d394916e20b12c7fe6ef9c39fbf525b9579cdc95130a&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;structure&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;maxDepth&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;sectionCount&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;memberCount&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;keysParsedCount&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;sectionNamePaths&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
                &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;User2&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;User2.PrefsOfUser2&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;User2.PrefsOfUser2.DeepSection&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;User2.PrefsOfUser2.DeepSection.DeeperSection&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;User2.PrefsOfUser2.DeepSection.DeeperSection.YetDeeperSection&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
            &lt;span class="p"&gt;]&lt;/span&gt;
        &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;metaSchemaVersion&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;1.1.1&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🛠️ CI &amp;amp; Tooling
&lt;/h3&gt;

&lt;p&gt;The repo now runs stronger checks on every PR &amp;amp; release:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Security:&lt;/strong&gt; CodeQL, npm audit, lockfile-lint, Gitleaks (SARIF), Semgrep (SARIF).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Grammar drift check:&lt;/strong&gt; Ensures ANTLR-generated sources are committed.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Regression tests:&lt;/strong&gt; Node/OS matrix coverage.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Releases:&lt;/strong&gt; npm publish with provenance (tag-driven).&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  💬 Other
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Parser summary logic and messages have been updated for clearer output.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  📦 Install / Upgrade
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install &lt;/span&gt;yini-parser@1.3.0-beta
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm update yini-parser
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  📚 Links
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://www.npmjs.com/package/yini-parser" rel="noopener noreferrer"&gt;yini-parser on npm&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;GitHub Repository&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;&lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;💡 This release lays groundwork for safer defaults and better developer ergonomics.&lt;/p&gt;

&lt;p&gt;Thanks for reading!&lt;/p&gt;

</description>
      <category>typescript</category>
      <category>node</category>
      <category>opensource</category>
    </item>
    <item>
      <title>🎉 YINI Parser v1.2.0-beta Released</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Sat, 13 Sep 2025 22:36:32 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-parser-v120-beta-released-ef2</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-parser-v120-beta-released-ef2</guid>
      <description>&lt;p&gt;Hi folks!&lt;/p&gt;

&lt;p&gt;I just published &lt;strong&gt;YINI Parser v1.2.0-beta&lt;/strong&gt; 🎊 — the latest beta release of the TypeScript/Node.js parser for the &lt;a href="https://github.com/YINI-lang/YINI-spec" rel="noopener noreferrer"&gt;YINI configuration format&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;This release comes with a mix of &lt;strong&gt;fixes, refactors, and quality-of-life improvements&lt;/strong&gt;, especially around runtime safety and metadata handling.&lt;/p&gt;

&lt;h2&gt;
  
  
  ✨ What's New
&lt;/h2&gt;

&lt;h3&gt;
  
  
  🛠️ Fixes
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;parseFile()&lt;/code&gt; now correctly passes through all options (e.g. &lt;code&gt;includeDiagnostics&lt;/code&gt;), so behavior now matches &lt;code&gt;parse(..)&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Fixed a small typo (&lt;code&gt;in in&lt;/code&gt;) in file parsing error messages.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  📊 Metadata Improvements
&lt;/h3&gt;

&lt;p&gt;The result metadata structure has been bumped to version 1.1.0.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="nx"&gt;preservesOrder&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;// Member/section order is implementation-defined, not mandated by the spec.&lt;/span&gt;
&lt;span class="nx"&gt;orderGuarantee&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;implementation-defined&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="nx"&gt;orderNotes&lt;/span&gt;&lt;span class="p"&gt;?:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These fields make it easier for tooling to reason about how order is preserved.&lt;/p&gt;

&lt;h3&gt;
  
  
  🔒 Safer Runtime
&lt;/h3&gt;

&lt;p&gt;The public &lt;code&gt;YINI&lt;/code&gt; class was refactored to use per-invocation runtime state.&lt;br&gt;
This prevents race conditions when multiple &lt;code&gt;parse(..)&lt;/code&gt; / &lt;code&gt;parseFile(..)&lt;/code&gt; calls run in parallel.&lt;/p&gt;

&lt;h3&gt;
  
  
  🗂️ File Layout &amp;amp; Naming
&lt;/h3&gt;

&lt;p&gt;To keep things consistent and tidy:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;src/parseEntry.ts → src/pipeline.ts&lt;/code&gt; (and &lt;code&gt;_parseEntry(..)&lt;/code&gt; → &lt;code&gt;runPipeline(..)&lt;/code&gt;).&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;core/types.ts&lt;/code&gt; → &lt;code&gt;core/internalTypes.ts&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Public-facing types/interfaces moved to &lt;code&gt;src/types/index.ts&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;src/yiniHelpers.ts&lt;/code&gt; → &lt;code&gt;src/utils/yiniHelpers.ts&lt;/code&gt;.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  🧹 Naming Consistency
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Renamed &lt;code&gt;includeMetaData&lt;/code&gt; → &lt;code&gt;includeMetadata&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;Replaced old &lt;code&gt;TJSObject&lt;/code&gt; type with the clearer &lt;code&gt;ParsedObject&lt;/code&gt; type throughout the codebase.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  📚 Documentation &amp;amp; Tests
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Expanded and improved &lt;strong&gt;TSDoc comments&lt;/strong&gt; across the public API.&lt;/li&gt;
&lt;li&gt;Unit tests are now colocated with source files (&lt;code&gt;src/**&lt;/code&gt;), ensuring 1:1 visibility between code and its tests.
This reduces the chance of missing coverage when refactoring.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  🚀 Why This Matters
&lt;/h3&gt;

&lt;p&gt;This release is all about stability and clarity:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;You get more accurate metadata out of the box.&lt;/li&gt;
&lt;li&gt;Safer runtime behavior when parsing concurrently.&lt;/li&gt;
&lt;li&gt;Cleaner project layout that makes contributing and navigating the repo easier.&lt;/li&gt;
&lt;li&gt;Better docs for anyone building on top of YINI Parser.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Code Example:
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;ParsedObject&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;YiniParseResult&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;../types&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;../YINI&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;YiniParseResult&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parseFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;myConfigFile.yini&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;includeMetadata&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🔗 Links
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;📦 npm: &lt;a href="https://www.npmjs.com/package/yini-parser" rel="noopener noreferrer"&gt;yini-parser&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;💻 GitHub: &lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;YINI Parser&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;📖 &lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  🙏 Feedback
&lt;/h3&gt;

&lt;p&gt;As always, feedback and contributions are super welcome! Try it out and let me know if you hit any edge cases.&lt;/p&gt;

</description>
      <category>node</category>
      <category>showdev</category>
      <category>opensource</category>
      <category>typescript</category>
    </item>
    <item>
      <title>YINI CLI v1.0.2-beta — Smarter Number Parsing 🚀</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Mon, 11 Aug 2025 17:26:43 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/yini-cli-v102-beta-smarter-number-parsing-3le9</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/yini-cli-v102-beta-smarter-number-parsing-3le9</guid>
      <description>&lt;p&gt;Just rolled out YINI v1.0.2-beta, and this one focuses on making the parser more capable and rock-solid when it comes to handling numbers.&lt;/p&gt;

&lt;h3&gt;
  
  
  🔧 What's New
&lt;/h3&gt;

&lt;p&gt;The internal YINI Parser has been upgraded to v1.0.2-beta, bringing full support for:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Negative values&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Edge cases across all number types:&lt;/p&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;- Integers
- Floats
- Hexadecimal
- Binary
- Octal
- Duodecimal (base-12)
- Exponential notation
&lt;/code&gt;&lt;/pre&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  💡 Why It Matters
&lt;/h3&gt;

&lt;p&gt;If you're working with configs that push the limits—maybe big integer IDs, scientific values, or alternative base notations—this update ensures they'll parse correctly, consistently, and without surprises.&lt;/p&gt;

&lt;h2&gt;
  
  
  Usage
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Installation
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Install it globally from npm&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Open your terminal and run:&lt;br&gt;
&lt;/p&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;npm install -g yini-cli
&lt;/code&gt;&lt;/pre&gt;

&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Test functionality&lt;/strong&gt;&lt;br&gt;&lt;br&gt;
Create a simple test file, for example: &lt;code&gt;config.yini&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
  name = 'My App Title'
  version = '1.2.3'
  pageSize = 25
  darkTheme = off
&lt;/code&gt;&lt;/pre&gt;


&lt;p&gt;Then run:&lt;br&gt;
&lt;/p&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;yini parse config.yini
&lt;/code&gt;&lt;/pre&gt;


&lt;p&gt;Expected result, your CLI should output a parsed version of the config and output something similar to:&lt;br&gt;
&lt;/p&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nl"&gt;App&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;My App Title&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;version&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.2.3&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;pageSize&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;25&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;darkTheme&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;    
&lt;/code&gt;&lt;/pre&gt;

&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  All Supported Number Format
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;In YINI config format below:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;        @yini

        ^ App
          name = 'My App Title'
          version = "1.2.3"
          pageSize = 25
          darkTheme = off

        ^ NumberFormats

          ^^ HexFormat              // Hexadecimal (base-16)
             hex    = #FF0066       // Default notation
             altHex = 0xFF0066      // Alternative notation
          ^^ BinFormat              // Binary (base-2)
             bin    = %10101111     // Default notation
             altBin = 0b10101111    // Alternative notation
          ^^ OctFormat              // Octal (base-8)
             oct    = 0o755         // (decimal 493)
          ^^ DozFormat              // Duodecimal (base-12)
             doz    = 0z10XE        // Default notation:     X=10, E=11
             altDoz = 0z10AB        // Alternative notation: A=10, B=11
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Will produce following JS object:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;App&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;My App Title&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;version&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.2.3&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;pageSize&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;25&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;darkTheme&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="nx"&gt;NumberFormats&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nl"&gt;HexFormat&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; 
      &lt;span class="na"&gt;hex&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;16711782&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;altHex&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;16711782&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="nx"&gt;BinFormat&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; 
      &lt;span class="nl"&gt;bin&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;175&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; 
      &lt;span class="nx"&gt;altBin&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;175&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="nx"&gt;OctFormat&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; 
      &lt;span class="nl"&gt;oct&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;493&lt;/span&gt; 
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="nx"&gt;DozFormat&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; 
      &lt;span class="nl"&gt;doz&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1859&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; 
      &lt;span class="nx"&gt;altDoz&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1859&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;    
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Links
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/YINI-lang/yini-cli/" rel="noopener noreferrer"&gt;yini-cli on GitHub&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/YINI-lang" rel="noopener noreferrer"&gt;YINI Project&lt;/a&gt;
&lt;em&gt;YINI home.&lt;/em&gt;
&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>programming</category>
      <category>node</category>
      <category>webdev</category>
      <category>tooling</category>
    </item>
    <item>
      <title>How to Use YINI Config Files in a Node.js App (with Real Examples)</title>
      <dc:creator>Mr Smithnen</dc:creator>
      <pubDate>Sat, 02 Aug 2025 23:29:53 +0000</pubDate>
      <link>https://dev.to/marko_kseppnen_6250a7f/how-to-use-yini-config-files-in-a-nodejs-app-with-real-examples-4e20</link>
      <guid>https://dev.to/marko_kseppnen_6250a7f/how-to-use-yini-config-files-in-a-nodejs-app-with-real-examples-4e20</guid>
      <description>&lt;p&gt;🙋‍♂️ &lt;strong&gt;Why I Wrote This&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;You know that moment when you're knee-deep in a side project and you just want a clean config file?&lt;br&gt;&lt;br&gt;
Something easier on the eyes than JSON, but more structured than old-school INI?&lt;/p&gt;

&lt;p&gt;That was me — and that's how &lt;strong&gt;YINI&lt;/strong&gt; started.&lt;/p&gt;

&lt;p&gt;Not to reinvent configuration formats, but just to make one that I wouldn't dread editing.&lt;/p&gt;

&lt;p&gt;In this post, I'll walk you through how to actually use YINI in a Node.js app, with real examples pulled straight from my own parser tests and tooling setup. It's simple, flexible, and (hopefully) a bit fun.&lt;/p&gt;


&lt;h3&gt;
  
  
  📦 Installing the Parser
&lt;/h3&gt;

&lt;p&gt;First, install the YINI parser from npm:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install &lt;/span&gt;yini-parser
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🧪 Parsing a Basic Config
&lt;/h3&gt;

&lt;p&gt;Let's start with a simple YINI config:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;^ App
title = 'My App Title'
items = 25
isDarkTheme = true
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here's how you load it in your app:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;yini-parser&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;config&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`
    ^ App
    title = 'My App Title'
    items = 25
    isDarkTheme = true
`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;config&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;App&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// 'My App Title'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;YINI &lt;strong&gt;requires strings to be quoted for&lt;/strong&gt; clarity.&lt;br&gt;
Numbers, booleans, and nulls are parsed correctly too — without weird surprises.&lt;/p&gt;

&lt;p&gt;The above config corresponds to this JavaScript object:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;App&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;My App Title&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;items&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;25&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;isDarkTheme&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  📂 Loading from a File
&lt;/h3&gt;

&lt;p&gt;In most real projects, you'll want to load your config from a file.&lt;br&gt;
&lt;code&gt;yini-parser&lt;/code&gt; provides a helper for that: &lt;code&gt;YINI.parseFile(..)&lt;/code&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;yini-parser&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;config&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parseFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./config.yini&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;config&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;App&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// e.g., 'My App Title'&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This works with &lt;code&gt;.yini&lt;/code&gt; files, and supports options like strict mode or metadata.&lt;/p&gt;

&lt;p&gt;Under the hood, &lt;code&gt;parseFile(..)&lt;/code&gt; just reads the file and passes it to &lt;code&gt;YINI.parse(..)&lt;/code&gt;. Simple and clean.&lt;/p&gt;

&lt;h3&gt;
  
  
  💡 Structured Config with Nested Sections
&lt;/h3&gt;

&lt;p&gt;Sometimes your config grows — and when it does, structure helps.&lt;br&gt;
YINI supports &lt;strong&gt;nested sections&lt;/strong&gt; (similar as to in Markdown) but with using caret-based indentation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@yini

^ App
name = "Nested Example"
version = "1.0.0"
debug = OFF

    ^^ Database
    host = "db.example.com"
    port = 3306
    user = "appuser"
    password = "dbpassword"

        ^^^ Pool
        min = 2
        max = 10
        idleTimeout = 300

    ^^ Logging
    level = "info"
    logToFile = ON
    filePath = "./logs/app.log"

/END
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can parse this in &lt;strong&gt;strict mode&lt;/strong&gt; like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;config&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;yiniString&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// true = strict mode&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The resulting object:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;App&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Nested Example&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;version&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.0.0&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;debug&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;Database&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;host&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;db.example.com&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;port&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3306&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;user&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;appuser&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;password&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;dbpassword&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;Pool&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;min&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;max&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;idleTimeout&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;300&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="na"&gt;Logging&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;level&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;info&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;logToFile&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;filePath&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./logs/app.log&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🛠 Optional Metadata
&lt;/h3&gt;

&lt;p&gt;Want more than just key/values?&lt;br&gt;
You can enable &lt;strong&gt;metadata mode&lt;/strong&gt; to get some stats and some other info — useful for diagnostics, etc.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;configWithMeta&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;YINI&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;yiniString&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;auto&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🗨️ Comments — Your Way
&lt;/h3&gt;

&lt;p&gt;YINI supports a variety of comment styles:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// This is a comment
# So is this
-- And this

/*
Block comments
are supported too
*/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ✅ Recap
&lt;/h3&gt;

&lt;p&gt;YINI isn't trying to be better than JSON, TOML, or YAML.&lt;br&gt;
It just tries to be clear, consistent, and pleasant to use — especially when you want nesting without indentation sensitivity, or strict validation without a mess of brackets.&lt;/p&gt;

&lt;p&gt;If you like working with structured configs in Node.js and want something that's:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Human-friendly&lt;/li&gt;
&lt;li&gt;Easy to read&lt;/li&gt;
&lt;li&gt;Tooling-ready&lt;/li&gt;
&lt;li&gt;Just structured enough…&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;🔗 Links&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;npm:&lt;/strong&gt; &lt;a href="https://www.npmjs.com/package/yini-parser" rel="noopener noreferrer"&gt;yini-parser&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GitHub:&lt;/strong&gt; &lt;a href="https://github.com/YINI-lang/yini-parser-typescript" rel="noopener noreferrer"&gt;YINI-lang/yini-parser-typescript&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href="https://yini-lang.org/?utm_source=devto&amp;amp;utm_medium=article&amp;amp;utm_campaign=yini_launch" rel="noopener noreferrer"&gt;YINI Homepage&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;– Marko&lt;br&gt;
&lt;em&gt;Creator of YINI&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Note: This article was originally published on Medium.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>node</category>
      <category>typescript</category>
      <category>javascript</category>
      <category>opensource</category>
    </item>
  </channel>
</rss>
