Julia: How to open a url into browser - url

You can open a link in Python with the webbrowser library:
import webbrowser
webbrowser.open('http://example.com')
In Julia, I can use the PyCall package to run the Python library:
using Pkg
Pkg.add("PyCall")
using PyCall
#pyimport webbrowser
webbrowser.open("http://example.com")
But is there a built-in function or package for Julia to open a link to your browser?

There's no built-in functionality afaict but you can use the open_in_default_browser function from LiveServer.jl (which in turn is from Pluto.jl).
$ julia -e 'using LiveServer; LiveServer.open_in_default_browser("https://example.com")'
I have LiveServer.jl installed in my root environment and it works great. I also use it to make a local web server using the serve. This is an alternative to using python -m http.server in a folder.
But if you don't want to install LiveServer.jl, you can just paste the code from LiveServer.jl into your startup.jl file.
function detectwsl()
Sys.islinux() &&
isfile("/proc/sys/kernel/osrelease") &&
occursin(r"Microsoft|WSL"i, read("/proc/sys/kernel/osrelease", String))
end
function open_in_default_browser(url::AbstractString)::Bool
try
if Sys.isapple()
Base.run(`open $url`)
return true
elseif Sys.iswindows() || detectwsl()
Base.run(`cmd.exe /s /c start "" /b $url`)
return true
elseif Sys.islinux()
browser = "xdg-open"
if isfile(browser)
Base.run(`$browser $url`)
return true
else
#warn "Unable to find `xdg-open`. Try `apt install xdg-open`"
return false
end
else
return false
end
catch ex
return false
end
end
There's also https://github.com/tpapp/DefaultApplication.jl and https://github.com/mgkuhn/Desktop.jl which I haven't used but you may want to check out.

You could consider using Electron:
using Electron
load(Window(), URI("https://github.com/julialang"))

Related

Use fdfind and fzf to open files in mpv

kdialog-open-files.lua and zenity-open-files.lua are two projects that use KDE KDialog and Gnome's zenity respectively to open files in mpv. I wish to do the same using fdfind and fzf.
As illustrated in this stackoverflow answer the following works and will be our starting point:
fdfind . /path/to/Music | fzf -m | xargs -d "\n" mpv
We can use the above command to select some files and play them using mpv. However we want a dialog to be created for our file selection. To do this, we create a bash script menu_fzf.sh with the following contents:
#!/bin/bash
urxvt -name fzf_menu -e bash -c "fzf -m $* < /proc/$$/fd/0 > /proc/$$/fd/1"
(urxvt is only an example and any other suitable terminal emulator can be used in the above).
Now if we run:
fdfind . /path/to/Music | menu_fzf.sh
then a new terminal opens that lets you pick multiple files from /path/to/Music with fzf and will return the selection as output to the calling terminal. So in fact right now we could run the following
fdfind . /path/to/Music | menu_fzf.sh | xargs -d "\n" mpv
and it will play the selected files in mpv. So far so good!
The tricky part now is how to do all the above using lua scripts from within mpv. By looking at the kdialog-open-files.lua or zenity-open-files.lua it seems I need to write something like this:
utils = require 'mp.utils'
-- TODO: make the following work so that file_select correctly stores
-- the files selected using menu_fzf.sh:
file_select = utils.subprocess({
args = {'command', 'argument1', 'argument2', 'and so on'},
cancellable = false,
})
-- and then the rest of the code from kdialog-open-files.lua
However I am finding the official manual for utils.subprocess to be terse and inadequate. I have creatively tried picking command, argument1, argument2, and so on in the above, but nothing seems to work!
So I have two questions:
Can you (please) complete the above code template into a working solution?
Do you know where I can find more information on utils.subprocess? Is there a more detailed manual somewhere? Where is the source-code?
Remark: As I have never programmed in lua before I am struggling with solving question-1 above and will probably continue to struggle even if I had the source code for utils.subprocess. So really help with question-1 is of higher priority. But any help with question-2 is also great!
My failed attempts so far:
The following will append all files in current directory to playlist:
file_select = utils.subprocess({
args = {'fdfind', '.', directory},
cancellable = false,
})
The following fails:
file_select = utils.subprocess({
args = {'fdfind', '.', directory, '|', 'fzf'},
cancellable = false,
})
with error message:
[open_files] [fd error]: Search path '|' is not a directory.
[open_files] [fd error]: Search path 'fzf' is not a directory.
The following allows selecting multiple files from $HOME directory but (as expected) does not return the selection:
file_select = utils.subprocess({
args = {'urxvt','-e','fzf', '-m'},
cancellable = false,
})
The following doesn't work:
file_select = utils.subprocess({
args = {'urxvt','-e','fzf', '-m', '>', '/proc/$$/fd/1'},
cancellable = false,
})
The following opens up a new dialog with fzf but has nothing to select from:
file_select = utils.subprocess({
args = {'menu_fzf.sh'},
cancellable = false,
})
Create a bash script mpv_fzf_menu.sh with the following content:
#!/bin/bash
urxvt -name fzf_menu -e bash -c "fdfind . "$1" | fzf -m > /proc/$$/fd/1"
Create a lua file open-files.lua with the following content:
utils = require 'mp.utils'
function select_files_dmenu_fzf()
if mp.get_property("path") == nill then
directory = ""
else
directory = utils.split_path(utils.join_path(mp.get_property("working-directory"), mp.get_property("path")))
end
file_select = utils.subprocess({
args = {'mpv_fzf_menu.sh', directory},
cancellable = false,
})
end
function add_files()
select_files_dmenu_fzf()
if (file_select.status ~= 0) then return end
local first_file = true
for filename in string.gmatch(file_select.stdout, '[^\n]+') do
mp.commandv('loadfile', filename, first_file and 'replace' or 'append')
first_file = false
end
end
mp.add_key_binding("Ctrl+f", "add-files-kdialog", add_files)
(I am assuming you know what to do next: make the bash script executable and put it somewhere where bash finds it in its $PATH. Put the lua script in .config/mpv/scripts and everything should work, i.e. - when you press Ctrl+f within mpv a dialog should open to let you select files).
Remark: All the functionalities of kdialog-open-files.lua have not been implemented. But the above lua script can be easily extended. You can further make things fancy by filtering for files with the specified extension with fdfind. And you can also use the bash script independent of the lua script. If you configure the --preview option of fzf then you can get a file preview before making selection.

LSP server on_init per project configuration

I'm noob in Lua and after many hours of searching, it wasn't successful.
I want to load some EFM language server configurations depends on a project setup. So, I found this: https://github.com/neovim/nvim-lspconfig/wiki/Project-local-settings
For example: in A project I have a "black" code formatter, in B project I have "yapf" code formatter.
After that I wrote custom on_init handler:
...
on_init = function(client)
-- We need to register only available linters and formatters, because it improves perfomance↴
local result = vim.fn.systemlist(
[[ poetry run pip list --disable-pip-version-check | grep -w -o '^black \|^yapf \|^flake8 \|^isort \|^mypy ' ]]
for _, package_name in pairs(result) do
local package_config = M[string.gsub(package_name, "%s+", "")]
if package_config then
table.insert(client.config.settings.languages.python, package_config)
end
end
client.notify("workspace/didChangeConfiguration")
return true
end,
...
Well, it works, but i have a problem with a custom command, it's sync and freezes UI on first LSP load. Is it possible to load on_init async or execute cmd async?

xonsh "which" equivalent - how to test if a (subprocess mode) command is available?

I would like to test (from xonsh) if a command is available or not. If I try this from the xonsh command prompt:
which bash
Then it works:
user#server ~ $ which bash
/usr/bin/bash
But it does not work from xonsh script:
#!/usr/bin/env xonsh
$RAISE_SUBPROC_ERROR = True
try:
which bash
print("bash is available")
except:
print("bash is not available")
Because it results in this error:
NameError: name 'which' is not defined
I understand that which is a shell builtin. E.g. it is not an executable file. But it is available at the xnosh command prompt. Then why it is not available inside an xonsh script? The ultimate question is this: how can I test (from an xonsh script) if a (subprocess mode) command is available or not?
import shutil
print(shutil.which('bash'))
While nagylzs' answer led me to the right solution, I found it inadequate.
shutil.which defaults to os.environ['PATH']. On my machine, the default os.environ['PATH'] doesn't contain the active PATH recognized by xonsh.
~ $ os.environ['PATH']
'/usr/bin:/bin:/usr/sbin:/sbin'
I found I needed to pass $PATH to reliably resolve 'which' in the xonsh environment.
~ $ $PATH[:2]
['/opt/google-cloud-sdk/bin', '/Users/jaraco/.local/bin']
~ $ import shutil
~ $ shutil.which('brew', path=os.pathsep.join($PATH))
'/opt/homebrew/bin/brew'
The latest version of xonsh includes a built-in which command. Unfortunately, the version included will emit an error on stdout if the target isn't found, a behavior that is not great for non-interactive use.
As mentioned in another answer, which exists in the current version of xonsh (0.13.4 as of 15/12/2022) so your script would work. However, it outputs its own error message so it's necessary to redirect stderr to get rid of it.
Also, unless you redirect its stdout as well (using all>), it migh be a good idea to capture its output so the final version would look like this:
#!/usr/bin/env xonsh
$RAISE_SUBPROC_ERROR = True
try:
bash = $(which bash err> /dev/null)
print(f"bash is available: {bash}")
except:
print("bash is not available")

How to package a single Python script with nix?

I have a single Python script called myscript.py and would like to package it up as a nix derivation with mkDerivation.
The only requirement is that my Python script has a run-time dependency, say, for the consul Python library (which itself depends on the requests and six Python libraries).
For example for myscript.py:
#!/usr/bin/env python3
import consul
print('hi')
How to do that?
I can't figure out how to pass mkDerivation a single script (its src seems to always want a directory, or fetchgit or similar), and also can't figure out how to make the dependency libraries available at runtime.
When you have a single Python file as your script, you don't need src in your mkDerivation and you also don't need to unpack any source code.
The default mkDerivation will try to unpack your source code; to prevent that, simply set dontUnpack = true.
myscript-package = pkgs.stdenv.mkDerivation {
name = "myscript";
propagatedBuildInputs = [
(pkgs.python36.withPackages (pythonPackages: with pythonPackages; [
consul
six
requests2
]))
];
dontUnpack = true;
installPhase = "install -Dm755 ${./myscript.py} $out/bin/myscript";
};
If your script is executable (which we ensure with install -m above) Nix will automatically replace your #!/usr/bin/env python3 line with one which invokes the right specific python interpreter (the one for python36 in the example above), and which does so in an environment that has the Python packages you've specifified in propagatedBuildInputs available.
If you use NixOS, you can then also put your package into environment.systemPackages, and myscript will be available in shells on that NixOS.
This helper function is really nice:
pkgs.writers.writePython3Bin "github-owner-repos" { libraries = [ pkgs.python3Packages.PyGithub ]; } ''
import os
import sys
from github import Github
if __name__ == '__main__':
gh = Github(os.environ['GITHUB_TOKEN'])
for repo in gh.get_user(login=sys.argv[1]).get_repos():
print(repo.ssh_url)
''
https://github.com/nixos/nixpkgs/blob/master/pkgs/build-support/writers/default.nix#L319

Windows commands in ruby

How do I run a Windows command in an Ruby app?
I am trying to run something like:
output = `cd #{RAILS_ROOT}/lib && java HelloWorld #{param1} #{param2}`
I print the result of the line above and paste it to a command prompt in Windows and it works just fine. However, when i run app and hit this code, output is blank rather than have a string I get back from HellowWorld. In HelloWorld I do a System.out.print("helloworld")
The following:
output = `cmd.exe /C dir`
puts "OUTPUT #{output}"
Returns:
OUTPUT
Issue in JRuby 1.5.3 fixed in JRuby 1.5.5:
http://www.jruby.org/2010/11/10/jruby-1-5-5.html
Try to use File#join here. It will generate crossplatform path for you
http://apidock.com/ruby/File/join/class
my_path = File.join(RAILS_ROOT, "lib")
output = `cd #{my_path} && java HelloWorld #{param1} #{param2}`
Also you can execute your system commands this way:
`cd #{my_path} && java HelloWorld #{param1} #{param2}`
system("cd #{my_path} && java HelloWorld #{param1} #{param2}")
%x[cd #{my_path} && java HelloWorld #{param1} #{param2}]
Related topic: System call from Ruby
Backticks work fine for me. Try:
output = `dir`
to prove to yourself that it's working. At that point, your question is how to run a Java app from the command line, or why your particular app isn't work. Note that you can temporarily change the working directory like this:
Dir.chdir(File.join(RAILS_ROOT,'lib')) do
output = `...`
end

Resources