saif
Hello everyone,
Long time lurker first time poster here. I’ve recently begun working on Elixir full-time again!
It’s been almost 3 years, and I’m really excited and having so much fun.
Having worked on some statically typed languages I’ve been using typespecs and Dialyzer a lot more in my day to day. And this particular message has been driving me crazy:
Function foo/1 has no local return
I just spent about 4 hours trying to figure out why Dialyzer was so upset. And it turned out it’s because when I want to refactor a type I forget to change it everywhere in the code. Dialyzer starts complaining and I can’t figure out why. So I end up having to pinpoint what’s causing the issue and then fixing it. A lot of the time it’s for something completely unrelated! Like for example using the %{ my_struct | key: val} update syntax to update a struct instead of struct(my_struct, key: val).
Has anybody else run into this issue before? And is there a way to help Dialyzer get better at pinpointing the exact issue?
Cheers!
Trending in Discussions
Other Trending Topics
Categories:
Sub Categories:
Forums
Popular Tags
- #ecto
- #liveview
- #troubleshooting
- #learning-elixir
- #deployment
- #library
- #erlang
- #testing
- #genserver
- #mix
- #absinthe
- #remote-other
- #otp
- #plug
- #how-to-question
- #macros
- #postgres
- #elixirconf
- #channels
- #exunit
- #discussion
- #code-sync
- #javascript
- #podcasts
- #onsite
- #dialyzer
- #docker
- #authentication
- #umbrella
- #full-time-contract
- #podcasts-by-brainlid
- #ecto-query
- #elixir-ls
- #blog-post
- #ai
- #phoenix_html
- #elixirconf-us
- #iex
- #graphql
- #genstage
- #websockets
- #supervisor
- #advent-of-code
- #distillery
- #processes
- #api
- #forms
- #hex
- #security
- #metaprogramming










Showing Posts 1 to 5- Show Best Posts
- Show All (oldest first)
- Show All (newest first)
Eiji
While I don’t know about any kind of universal solutions you can take a look at this article:
Dialyzer, or how I learned to stop worrying and love the cryptic error messages
There is also one useful
hexpackage:In case you have no idea what
dialyzeris trying to say you can usedialyxirmix task:NobbZ
The error
has no local returnmeans that dialyzer can not find a path that won’t raise or throw.This warning is undebuggable without having more insight into the code.
globalkeith
Function foo/1 has no local returnmeans your function is not total - somewhere the code path would result in your function not returning a value.Whilst these investigations sometimes take time, in my experience, two things happen.
Finally, in my experience, whether you like it or not Dialyzer is always right.
The example you gave, one could result in a
KeyErrorwhereas the other ignores the error:NobbZ
It does not mean that. It does mean that from dialyzers perspective the mentioned function will always raise. Not that it has some code path that will raise.
Understanding how dialyzer thinks that it will always raise requires an analisis of the function mentioned, as well as its nested functions.
I have experienced quite often that the problem was some NIF replacement function that raised, rather than calling
:erlang.nif_error/1,2.In many other cases it was some situation in which wrongly declared typespecs misleaded dialyzer to make assumptions that were not matching runtime behaviour.
saif
I think this was the case for me the majority of the time.