# ANN: Infiltrator.jl

**URL:** <https://discourse.julialang.org/t/ann-infiltrator-jl/28323>\
**Category:** Package Announcements\
**Tags:** package, announcement, debug, debugging\
**Created:** [September 3, 2019, 11:58am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323 "2019-09-03T11:58:53Z")\
**Posts on this page:** 20\
**Page:** 1

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 3, 2019, 11:58am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/1 "2019-09-03T11:58:53Z")

</div>

Hey everyone,

I’d like to announce [Infiltrator.jl](https://github.com/JuliaDebug/Infiltrator.jl), which is intended as complement to the existing debuggers.

### What is this?

Infiltrator.jl provides a macro called `@infiltrate` , which sets a “breakpoint” in a local context (similar to Matlab’s `keyboard` function). The advantage of this macro over e.g. Debugger.jl is that all code is completely compiled, so the performance overhead should be negligible.

`@infiltrate` will drop you into an interactive REPL session that lets you inspect local variables and the call stack as well as execute arbitrary statements in the context of the current function’s module. You can optionally supply an argument to `@infiltrate` (that must evaluate to a boolean) to make it conditional.

Note that you cannot access other functions in the callstack, or step into functions. If you need that functionality, use Debugger.jl or Juno’s debugger.

### Installation

```julia-auto
pkg> add Infiltrator

```

### Usage

```julia-auto
julia> function f(x)
         x *= 2
         y = rand(3)
         @infiltrate
         x += 2
       end
f (generic function with 1 method)

julia> f(3)
Hit `@infiltrate` in f(::Int64) at none:4:

debug> ?
Code entered is evaluated in the current function's module. 
Note that you cannot change local variables.
The following commands are special cased:
- `@trace`: Print the current stack trace.
- `@locals`: Print local variables.

Exit this REPL mode with `Ctrl-D`.

debug> @trace
[1] f(::Int64) at none:4
[2] top-level scope at none:0

debug> @locals
- y::Array{Float64,1} = [0.187253, 0.145958, 0.183677]
- x::Int64 = 6

debug> x.+y
3-element Array{Float64,1}:
6.187252565686353
6.145958004935359
6.1836766675450034

debug>^D
8

julia>

```

---

<div class="post-metadata">

**Author:** ![00vareladavid](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/00vareladavid/32/23521_2.png) [@00vareladavid](https://discourse.julialang.org/u/00vareladavid)\
**Post date:** [September 3, 2019, 12:03pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/2 "2019-09-03T12:03:03Z")

</div>

Excellent name!

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 3, 2019, 12:05pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/3 "2019-09-03T12:05:36Z")

</div>

@BeastyBlacksmith [came up with that](https://github.com/JuliaDebug/Infiltrator.jl/issues/1#issuecomment-524824386), but yes, I agree 🙂

---

<div class="post-metadata">

**Author:** ![dawbarton](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/dawbarton/32/215461_2.png) [@dawbarton](https://discourse.julialang.org/u/dawbarton)\
**Post date:** [September 3, 2019, 12:33pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/4 "2019-09-03T12:33:17Z")

</div>

This is great! You’ve covered 90% of my use cases for debugger with this. I’m also impressed with how simple the package is as well - just over 200 lines and basically no dependencies! (I also like the name 🙂)

---

<div class="post-metadata">

**Author:** ![jlperla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jlperla/32/34332_2.png) [@jlperla](https://discourse.julialang.org/u/jlperla)\
**Post date:** [September 3, 2019, 4:56pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/5 "2019-09-03T16:56:31Z")

</div>

I love the idea. This is a good portion of what people do when use debuggers for exploration. This still requires modifying the files, but it is a step forward.

Does it currently support/or are you planning to support showing the locals in the Juno panes? Are you also considering this as a debugging option in Juno in general (i.e. people could choose to either run the fully interpreted version with all of the flexibilty, or this faster version for just exploring the state of the computation)?

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 3, 2019, 5:07pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/6 "2019-09-03T17:07:11Z")

</div>

[Yes](https://github.com/JuliaDebug/Infiltrator.jl/issues/2). I suppose we could also re-use the breakpoint UI and pretend no-one modified their source code, but not sure if that’s a good idea or not.

---

<div class="post-metadata">

**Author:** ![jlperla](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jlperla/32/34332_2.png) [@jlperla](https://discourse.julialang.org/u/jlperla)\
**Post date:** [September 3, 2019, 5:24pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/7 "2019-09-03T17:24:46Z")

</div>

> [@pfitzseb](#):
>
> not sure if that’s a good idea or not.

I would be very helpful for usability of low tech debugger users. In matlab you can both modify the code/local variables and still run it full speed between breakpoints. We won’t be there in Julia for a while, so I think it is reasonable to make people choose what they want. Most cases will be of the second type where infiltrator (if I understand it) is the solution. If the UI makes the choice clear (ie high speed exploration vs interpreted full control), then people will no longer be perplexed that the code runs orders of magnitude slower while debugging

---

<div class="post-metadata">

**Author:** ![joa-quim](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/joa-quim/32/227_2.png) [@joa-quim](https://discourse.julialang.org/u/joa-quim)\
**Post date:** [September 3, 2019, 6:43pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/8 "2019-09-03T18:43:22Z")

</div>

Hmm, I’m getting this

```julia
julia> cd("c:/v");using GMT, Infiltrator
[Info: Precompiling GMT [5752ebe1-31b9-557e-87aa-f909b540aa54]
[Info: Precompiling Infiltrator [5903a43b-9cc3-4c30-8d17-598619ec4e9b]

julia> imshow(GMT.peaks(), view=:default, zaxis=(annot=:auto, grid=:auto), Vd=2)
LoadError: UndefVarError: @infiltrate not defined

```

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 3, 2019, 6:45pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/9 "2019-09-03T18:45:32Z")

</div>

You need to make sure `@infiltrate` is available in whatever scope you’re using it in. In this case something like

```julia
Main.Infiltrator.@infiltrate

```

in your package code should work fine. The other option is, of course, to put the `using Infiltrator` into your package.

---

<div class="post-metadata">

**Author:** ![joa-quim](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/joa-quim/32/227_2.png) [@joa-quim](https://discourse.julialang.org/u/joa-quim)\
**Post date:** [September 3, 2019, 6:48pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/10 "2019-09-03T18:48:08Z")

</div>

Thanks, `Main.Inf....` worked.

---

<div class="post-metadata">

**Author:** ![Amin\_Yahyaabadi](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/amin_yahyaabadi/32/9826_2.png) [@Amin\_Yahyaabadi](https://discourse.julialang.org/u/Amin_Yahyaabadi)\
**Post date:** [September 3, 2019, 9:47pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/11 "2019-09-03T21:47:22Z")

</div>

Debugging in Julia was an issue, and just to check a variable value inside a function you had to go through the slow debugging process. But not anymore! 🎉  
This is exactly [what I wanted](https://github.com/JuliaDebug/JuliaInterpreter.jl/issues/298) .

Atom/Juno integration will be certainly useful.

---

<div class="post-metadata">

**Author:** ![xiaodai](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/xiaodai/32/15937_2.png) [@xiaodai](https://discourse.julialang.org/u/xiaodai)\
**Post date:** [September 3, 2019, 10:42pm UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/12 "2019-09-03T22:42:28Z")

</div>

Found variable inspection to be a pain in other debuggers. Going to give this a spin

---

<div class="post-metadata">

**Author:** ![kmundnic](https://avatars.discourse-cdn.com/v4/letter/k/e19adc/32.png) [@kmundnic](https://discourse.julialang.org/u/kmundnic)\
**Post date:** [September 4, 2019, 3:37am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/13 "2019-09-04T03:37:49Z")

</div>

Is there a minimum Julia version required? I was able to install in v1.2. In v1.0.4, it is throwing this error:

```julia
(v1.0) pkg> add Infiltrator
  Updating registry at `~/.julia/registries/General`
  Updating git-repo `https://github.com/JuliaRegistries/General.git`
 Resolving package versions...
ERROR: Unsatisfiable requirements detected for package Infiltrator [5903a43b]:
 Infiltrator [5903a43b] log:
 ├─possible versions are: 0.1.0 or uninstalled
 ├─restricted to versions * by an explicit requirement, leaving only versions 0.1.0
 └─restricted by julia compatibility requirements to versions: uninstalled — no versions left

```

---

<div class="post-metadata">

**Author:** ![00vareladavid](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/00vareladavid/32/23521_2.png) [@00vareladavid](https://discourse.julialang.org/u/00vareladavid)\
**Post date:** [September 4, 2019, 4:10am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/14 "2019-09-04T04:10:27Z")

</div>

It is registered as compatible with julia 1.1 or higher

---

<div class="post-metadata">

**Author:** ![StevenSiew](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevensiew/32/218393_2.png) [@StevenSiew](https://discourse.julialang.org/u/StevenSiew)\
**Post date:** [September 4, 2019, 5:49am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/15 "2019-09-04T05:49:36Z")

</div>

Can you do conditional Infiltrator? For example

```julia
if x > 7 && y < 29
    Main.Infiltrator.@infiltrate
end

```

---

<div class="post-metadata">

**Author:** ![baggepinnen](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/baggepinnen/32/693_2.png) [@baggepinnen](https://discourse.julialang.org/u/baggepinnen)\
**Post date:** [September 4, 2019, 5:51am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/16 "2019-09-04T05:51:14Z")

</div>

> [@pfitzseb](#):
>
> You can optionally supply an argument to `@infiltrate` (that must evaluate to a boolean) to make it conditional.

Yes

---

<div class="post-metadata">

**Author:** ![Amval](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/amval/32/6217_2.png) [@Amval](https://discourse.julialang.org/u/Amval)\
**Post date:** [September 4, 2019, 7:29am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/17 "2019-09-04T07:29:42Z")

</div>

Really useful! I seem to be having a weird issue, though: first time that I type into \>debug it doesn’t recognize all characters.

For example, typing @locals it only gets @lsl.

Is anyone experiencing simillar problems? Shall I open a GitHub issue?

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 4, 2019, 8:15am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/18 "2019-09-04T08:15:27Z")

</div>

Are you by chance using Juno’s/VSCode’s inline evaluation for executing a function that calls `@infiltrate` somewhere down the call stack? If so, that’s a known problem, and the only workaround is to call your function in the REPL.

---

<div class="post-metadata">

**Author:** ![pfitzseb](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/pfitzseb/32/45566_2.png) [@pfitzseb](https://discourse.julialang.org/u/pfitzseb)\
**Post date:** [September 4, 2019, 8:22am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/19 "2019-09-04T08:22:42Z")

</div>

> [@kmundnic](#):
>
> Is there a minimum Julia version required? I was able to install in v1.2. In v1.0.4, it is throwing this error:

> [@00vareladavid](#):
>
> It is registered as compatible with julia 1.1 or higher

Yup, Infiltrator uses `@locals`, which is only available with Julia 1.1, unfortunately.

---

<div class="post-metadata">

**Author:** ![Amval](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/amval/32/6217_2.png) [@Amval](https://discourse.julialang.org/u/Amval)\
**Post date:** [September 4, 2019, 8:22am UTC](https://discourse.julialang.org/t/ann-infiltrator-jl/28323/20 "2019-09-04T08:22:50Z")

</div>

Ah, yes, I am. Thank you for the quick response.

I suppose this is due to some underlying Juno issue?

[Next page](https://discourse.julialang.org/t/ann-infiltrator-jl/28323.md?page=2)
