# Sysrift v0.1.0 release

**URL:** <https://forum.crystal-lang.org/t/sysrift-v0-1-0-release/8835>\
**Category:** News\
**Created:** [March 31, 2026, 12:24pm UTC](https://forum.crystal-lang.org/t/sysrift-v0-1-0-release/8835 "2026-03-31T12:24:23Z")\
**Posts on this page:** 1\
**Showing post:** 5

<div class="post-metadata">

**Author:** ![straight-shoota](https://yyz2.discourse-cdn.com/flex036/user_avatar/forum.crystal-lang.org/straight-shoota/32/36_2.png) [@straight-shoota](https://forum.crystal-lang.org/u/straight-shoota)\
**Post date:** [April 7, 2026, 9:43am UTC](https://forum.crystal-lang.org/t/sysrift-v0-1-0-release/8835/5 "2026-04-07T09:43:43Z")

</div>

> [@xalynn](#):
>
> I was comparing `stat.owner_id == 0` instead of `== "0"`. Crystal doesn’t complain since String == Int is valid syntax, it just silently evaluates to false. Every SUID binary was bypassing my root-owner filter and I couldn’t figure out why until I tested it in crystal eval.

I wish Crystal had type-safe equality.

> <https://github.com/crystal-lang/crystal/issues/10277>
>
> I realized that Crystal currently allows comparisons that always fail:
> 
> \`\`\`cr
> …
> "a" == 'a' # Not comparable, but accepted by compiler and always returns false
> SomeEnum::Member == 10 # Same here (\`SomeEnum != Int32\` but again accepted and returns false)
> \`\`\`
> 
> I asked on Crystal chat and @asterite and @straight-shoota report that comparing anything to anything (defaulting to returning \`false\`) was allowed because otherwise comparing union types would be problematic, and the language would be too rigid. Previous or similar tickets about this issue, which explain it, are #2996, #6154, and #8893. (And #1730 which asks about the same issue.)
> 
> (For a very brief example, if such comparisons were prevented, they would have prevented some very reasonably-looking code from working, such as: \`{1, "a", nil}.includes? 'x'\`)
> 
> In any case, the reason why these comparisons are allowed (and always returning false) is this fallback implementation of \`#==\` in types \`Value\` and \`Reference\`:
> 
> \`\`\`cr
> # Returns \`false\`.
> def ==(other)
> false
> end
> \`\`\`
> 
> This seems to me as undesirable because it (1) removes type safety from arguably the most basic operator in a language (\`==\`), and also it partially masks \`Comparable\`.
> 
> I think that both arguments:
> 
> 1) Being able to compare anything to anything, returning false
> 2) Asking for type safety in a comparison operator
> 
> Are completely valid, and in fact they represent two different use cases which shouldn't be hidden behind a single \`#==\` operator.
> 
> My suggestion is that we add a new operator which implements the other case.
> 
> Option 1:
> The default implementation of \`#==\` is removed, so that the only working \`#==\` comes from \`Comparable\` or a specific implementation of \`#==\`, and is type safe.
> Another operator (for example \`==?\`) is added which does what \`#==\` currently does (returns \`false\` as a fallback).
> 
> Option 2:
> \`#==\` is left as-is, and another operator is added, which enforces type checks.
> 
> I think option 1 would be clean and consistent, certainly preferrable, and option 2 would maybe be easier/more viable, all things considered.
> 
> @straight-shoota mentioned that he was preparing an RFC about this issue.
> @asterite said: "It would be nice if equality was type safe. Someone can try it and see how hard it is to make the std specs pass with that change, and how the code changes."
> 
> Comments welcome.

---

_[View the full topic](https://forum.crystal-lang.org/t/sysrift-v0-1-0-release/8835)._
