I want to make a plugin for neovim using the Python API (pynvim). The problem is I want to get the current buffer's text, updated real time. I have searched on the web and didnt find any useful (or understandable) documentation for this.
You can use pynvim to subscribe to an event in neovim. Do keep in mind that pynvim is async, but my example is using a simple while loop do demonstrate how to monitor for realtime change in a buffer and get its content.
from time import sleep
from pynvim import attach, api
nvim = attach('socket', path='/tmp/nvim')
buffer = nvim.current.buffer
event = api.nvim.Nvim.from_nvim(nvim) # use the loaded nvim session
listen = event.subscribe('TextChangedI') # refer to events https://neovim.io/doc/user/autocmd.html#events
while True:
sleep(2)
print(listen)
# read and print contents of the whole buffer
for line in range(len(buffer)):
print(buffer[line])
Related
I have a script running on my raspberry, these script is started from a command from an php page. I’ve multiple if stetements, now I would like to pass new arguments to the script whithout stopping it. I found lots of information by passing arguments to the python script, but not if its possible while the svpcript is already running to pass new arguments. Thanks in advance!
The best option for me is to use a configuration file input for your script.
Some simple yaml will do. Then in a separate thread you must observe the hash of the file, if it gets changed that
means somebody has updated your file and you must re/adjust your inputs.
Basically you have that constant observer running all the time.
You need some sort of IPC mechanism really. As you are executing/updating the script from a PHP application, I'd suggest you'll look into something like ZeroMQ which supports both Python and PHP, and will allow you to do a quick and dirty Pub/Sub implementation.
The basic idea is, treat your python script as a subscriber to messages coming from the PHP application which publishes them as and when needed. To achieve this, you'll want to start your python "script" once and leave it running in the background, listening for messages on ZeroMQ. Something like this should get you going
import zmq
context = zmq.Context()
socket = context.socket(zmq.REP)
socket.bind("tcp://*:5555")
while True:
# Wait for next message from from your PHP application
message = socket.recv()
print("Recieved a message: %s" % message)
# Here you should do the work you need to do in your script
# Once you are done, tell the PHP application you are done
socket.send(b"Done and dusted")
Then, in your PHP application, you can use something like the following to send a message to your Python service
$context = new ZMQContext();
// Socket to talk to server
$requester = new ZMQSocket($context, ZMQ::SOCKET_REQ);
$requester->connect("tcp://localhost:5555");
$requester->send("ALL THE PARAMS TO SEND YOU YOUR PYTHON SCRIPT");
$reply = $requester->recv();
Note, I found the above examples using a quick google search (and amended slightly for educational purposes), but they aren't tested, and purely meant to get you started. For more information, visit ZeroMQ and php-zmq
Have fun.
I've written a script that periodically scrapes twitter data using while True.
For the except element, I initiate a one-time scrape of a large chunk of data.
The only way I can trigger this is by using Ctrl+C. What I want to do is map the 'Ctrl+C' function to the button on my RaspberryPi Pibrella.
I've looked around here, there, and everywhere, but had no joy. The only module I can find does not work on Raspberry Pi (Linux).
def status_update():
while True:
try:
scrape_some_stuff()
time.sleep(1x60)
except:
scrape_lots_of_stuff()
time.sleep(1x60)
pibrella has a package (pip install pibrella) so you can easily monitor the button status, with which you can use to raise your exception
import pibrella
# add this line into your codes
pibrella.button.pressed(raise Exception)
Their github repo has some examples.
I want to write a Python script that checks whether my device has a display and whether that display is turned on or off.
I googled it, there is a third-party library named "WMI", but it can only get some information like CPU/HDD/process/thread, so I am confused about it.
I am using Windows 10, in case that matters.
Is it possible to get that kind of low level hardware information via Python, and if it is, how can I do it?
It looks like Windows does not really have a way to tell you if the monitor is on or off. The WMI Win32_DesktopMonitor class has an 'Availability' property but this doesn't seem to be affected by changing the monitor state. I tested this using the following python script:
import wmi # pip install WMI
import win32gui, win32con
SC_MONITORPOWER = 0xF170
wmic = wmi.WMI()
def powersave():
# Put the monitor to Off.
win32gui.SendMessage(win32con.HWND_BROADCAST, win32con.WM_SYSCOMMAND, SC_MONITORPOWER, 2)
# Get the monitor states
print([monitor.Availability for monitor in wmic.Win32_DesktopMonitor()])
if __name__ == '__main__':
powersave()
The SC_MONITORPOWER arguments are documented here.
Unfortunately the result for my monitor is always 3 which means it is "on", even when it is actually powered down either in sleep mode or physically off.
Depending on your requirement, you might just want to send the broadcast message to assert the power state you want and not need to check the current state.
I am trying to record a live stream in vlc. It is easy if I use the GUI, just clicking on Convert/Save in the Media option, and after that choosing the stream address in the Network tab. I wanted to do the same thing in a C/C++/Python program. In case of a C program, I used Visual Studio but on writing #include<vlc/vlc.h> it says the file cannot be included. Then I downloaded the source from git but still it is not working. What to do?
You can save a stream using commandline arguments:
vlc scheme://host/stream.xyz --sout file/muxer:stream.xyz
and thus, call it using some kind of exec() (or its windows equivalent).
Then, the following answer: https://stackoverflow.com/a/19484168/1290438 shows how to open a stream in VLC in python:
import vlc
i = vlc.Instance('--verbose 2'.split())
p = i.media_player_new()
p.set_mrl('rtp://#224.1.1.1')
p.play()
So I guess, at worst, you can give the --sout argument to vlc.Instance, or at best there's a method on the instance to set up stream output.
In my humble opinion, using C/C++ for such a simple task is like killing a fly using a bazooka…
Background: I have a python program that imports and uses the readline module to build a homemade command line interface. I have a second python program (built around bottle, a web micro-framework) that acts as a front-end for that CLI. The second python program opens a pipe-like interface to the first, essentially passing user input and CLI output back and forth between the two.
Problem: In the outer wrapper program (the web interface), whenever the end-user presses the TAB key (or any other key that I bind the readline completer function), that key is inserted into the CLI's stdin without firing the readline completer function. I need this to trigger readline's command completion function instead, as normally occurs during an interactive CLI session.
Possible Solution #1: Is there some way to send the TAB key to a subprocess' stdin, so that a batch usage works the same as an interactive usage?
Possible Solution #2: Or, if there was some way to trigger the entire completion process manually (including matches generation and display), I could insert and scan for a special text sequence, like "<TAB_KEY_HERE>", firing the possible completion matches display function manually. (I wrote the completer function, which generates the possible matches, so all I really need is access to readline's function to display the possible matches.)
Possible Solution #3: I guess, if I cannot access readline's matches-display function, the last option is to rewrite readline's built-in display-completion function, so I can call it directly. :(
Is there a better solution? Any suggestions on following the paths presented by any of the above solutions? I am stuck on #1 and #2, and I'm trying to avoid #3.
Thanks!
Solution #1 proved to be a workable approach. The key was to not connect the web socket directly to the CLI app. Apparently, readline was falling back into some simpler mode, which filtered out all TAB's, since it was not connected to a real PTY/TTY. (I may not be remembering this exactly right. Many cobwebs have formed.) Instead, a PTY/TTY pair needed to be opened and inserted in between the CLI app and web-sockets app, which tricked the CLI app into thinking it was connected to a real keyboard-based terminal, like so:
import pty
masterPTY, slaveTTY = pty.openpty()
appHandle = subprocess.Popen(
['/bin/python', 'myapp.py'],
shell=False,
stdin=slaveTTY,
stdout=slaveTTY,
stderr=slaveTTY,
)
...
while True
# read output from CLI app
output = os.read(masterPTY, 1024)
...
# write output to CLI app
while input_data:
chars_written = os.write(masterPTY, input_data)
input_data = input_data[chars_written:]
...
appHandle.terminate()
os.close(masterPTY)
os.close(slaveTTY)
HTH someone else. :)
See this answer to a related question for more background:
https://stackoverflow.com/a/14565848/538418