I have developed a multi-platform desktop application in python and PyQt and in it i want to implement the concept of impersonation. I have a requirement where user selects a file and the the application will check for naming conventions and other things. If everythin is fine then it copies the file in a server where only impersonate user lets say (user123) has full permissions other has only read permissions.
I could able to achieve this in windows by using win32security and win32con
TO IMPERSONATE LOGIN
Self.handel=win32security.LogonUser(self.loginID,self.domain,self.password,win32con.LOGON32_LOGON_INTERACTIVE,win32con.LOGON32_PROVIDER_DEFAULT)
win32security.ImpersonateLoggedOnUser(self.handel)
AND TO REVERT BACK TO USER
win32security.RevertToSelf()
Can anyone suggest an approach to this under Linux (RHEL 6).
First, think whether your task actually needs OS-level impersonation.
If you use e.g. PySmbClient to access a Windows file share, then you manage all connections yourself and you can just give different credentials to smbclient.
If you use PyKDE4.kio, as far as I know the same applies (KIO uses smbclient).
If you access the file server over an existing system-level mount, there is no actual "impersonation" as in Windows; it is done by simply changing the process' "effective UID" and generally can be done only if the program has root privileges (or the root-equivalent CAP_SETUID privilege on Linux).
uid = pw.getpwnam(username).pw_uid
os.seteuid(uid)
...
os.seteuid(0)
(This is not guaranteed to work with network filesystems that store credentials in kernel keyrings... I don't yet have an answer for that.)
However, most desktop programs do not have root privileges (and should not have them). In that case, seteuid() is unavailable, and privileged actions are normally done by a privileged daemon that the desktop app contacts using some form of IPC (usually D-Bus).
Related
Morning,
I have implemented a script that is run every day that needs to check if an email, with predetermined parameters, has arrived.
The script works and opens outlook only if I am logged in on the machine.
If I run the process without being logged in on the machine, the script does not interface with outlook (be clear does not give errors).
I attach the code.
import win32com.client
outlook = win32com.client.Dispatch('outlook.application')
mapi = outlook.GetNamespace("MAPI")
inbox = mapi.GetDefaultFolder(6)
messages = inbox.Items.Restrict("[Unread]=true")
messages = messages.Restrict("[Subject] = 'XXXX')
Can you provide support ?
If I run the process without being logged in on the machine, the script does not interface with outlook (be clear does not give errors).
Outlook may not recognize the profile to open without logging in.
Also Microsoft does not currently recommend, and does not support, Automation of Microsoft Office applications from any unattended, non-interactive client application or component (including ASP, ASP.NET, DCOM, and NT Services), because Office may exhibit unstable behavior and/or deadlock when Office is run in this environment.
If you are building a solution that runs in a server-side context, you should try to use components that have been made safe for unattended execution. Or, you should try to find alternatives that allow at least part of the code to run client-side. If you use an Office application from a server-side solution, the application will lack many of the necessary capabilities to run successfully. Additionally, you will be taking risks with the stability of your overall solution.
Read more about that in the Considerations for server-side Automation of Office article.
In summary; I want to be able to interact with a non-logged in steam client and log it in, and I dont want to use some type of Windows only interaction. I don't mean the SteamCLI, or logging into steam using the steam library for python. I mean directly interacting with the steam client in some way and physically logging in.
When using SteamCLI and other modules I've noticed it just logs you into their session instead of the client session that you get from physically logging into steam.
for example:
from steam.client import SteamClient
x = SteamClient()
x.login(username=, password=)
Doesn't actually log you in, since it is its own client.
I need this because I have made a script that can connect me to servers and figure out who's on it, and it relies on you being logged in to said client.
Is there any modules/libraries that will allow me to do this? and if pywinauto is the one I should use, are there any guides you know of so I can interact with said application in a good way, even on linux.
So here is what I ended up doing:
First you get a dummy display. I used this https://askubuntu.com/questions/453109/add-fake-display-when-no-monitor-is-plugged-in
After that you create the config (https://askubuntu.com/a/463000) and start up the display.
Next I created a systemd unit to launch steam using command line
[Unit]
Description=example systemd service unit file.
[Service]
User=root
Environment=XAUTHORITY=/var/run/lightdm/root/:0
Environment=DISPLAY=:0
ExecStart=/bin/bash /root/start.sh
[Install]
WantedBy=multi-user.target
(you probably shouldn't be using root for this, but its the easiest way I found to always have perms to the XAUTHORITY env, so you can login to the display)
Here is what /root/start.sh looks like
#!/bin/sh
export DISPLAY=:0
export XAUTHORITY=/var/run/lightdm/root/:0
export PATH="$PATH:/usr/games"
steam -login username_goes_here password_goes_here steam_guard_code
Note that you may not need to do the export DISPLAY and export XAUTHORITY twice. I haven't tested it.
This should just workâ˘, it will log in, but it will ask for a steam guard code, so what you should do is attempt to start the service, receive the code through email, then append it after password.
As for doing this in python, as I said originally. you can probably use it to call start.sh, implementing command line arguments for steam code. You need these arguments because I haven't found a way for it to trust the computer you use, so it might be beneficial to implement python IMAP for reading the codes sent to the email which owns the account and using said arguments.
Theoretical Section
Please note this whole section is untested, but intended to answer my original question.
Heres what a python file might look like (very roughly)
def start_steam(code=""):
# Assuming start.sh includes reading variables from cmd line (my example didnt)
proc = subprocess.Popen(["/bin/bash", "start.sh", code])
# This function would probably just interact iwth an IMAP server to retrieve an email sent by steam support with the code. If its not found within a certain range of time, it would theoretically just stop looking
steam_guard_code = do_something_to_find_steam_guard_code_email(timeout=30)
if code:
proc.terminate()
start_steam(code=code)
else:
# proc should continue to run in the background, until restart, that means this script should ALSO run on startup, or until there isnt a PID detected for steam
with open("/var/run/steam.pid", "w") as f:
f.write(process.pid)
exit()
this python script would have to be run by systemd, it would be a forking process, and PIDfile would have to be specified by systemd (I think) so that it can be monitored.
edit: this solution has become even more theoretical, since it is not possible to pass steam guard code to steam -login username password. You would need to disable steam guard.
The business case...
The app server (Ubuntu/nginx/postgresql/python) that I use writes gzipped system log files as root to /var/log
I need to present data from these log files to users' browsers
My approach
I need to do a fair bit of searching and string manipulation server side so I have a python script that deals with the opening and processing and then returns a nicely formatted JSON result set. The python (cgi) script is then called using ajax from the web page.
My problem
The script works perfectly when called from the command line as SU but (...obviously) the file opening method I'm using ( gzip.open(filename) ) is failing when invoked as user www-data by the webserver.
Other useful info
The app server concerned is (contractually rather than physically) a bit of a black box - I have SU access, I can write scripts, I can read anything but I can't change file permissions, add additional python libs or or mess with config.
The subset of users who can would use this log extract also have the SU password so could be presented with a login dialog that I could pass to the script.
Given the restrictions I have, how would you go about it?
One option would be to do this somewhat sensitive "su" work in a background process that is disconnected from the web.
Likely running via cron, this script would take the root owned log files, possibly change them to a format that the web-side code could deal with easily like loading them into a database, or merely unzipping them and placing them into a different location with slightly more laxed permissions.
Then the web-side code could easily have access to the data without having to jump through the "su" hoops.
From my perspective this plan does not seem to violate your contractual rules. The web server config, permissions, etc remain intact.
My two cents. You should give a try to paramiko, allowing you to access a host (even "localhost") through SSH:
import paramiko
ssh = paramiko.SSHClient()
ssh.connect('127.0.0.1', username='jesse', password='lol')
As you have the opportunity to ask for a login/password, those would be the one provided by the user querying the log. Accessing the files is then just a matter or reading a file under SSH. And you have the opportunity to close the connection as soon as you have finished that "sensitive" work.
For various reasons I can't use login.py to log me in so I was wondering if anyone knew code so that I could log in to Wikipedia with my script without running a separate script?
Cheers!
The answer is going to be simple: you can't use pywikipedia without being able to run login.py.
That file not only provides a nice User-interface to try your configuration: it contains all the authentication primitives that we use in the framework to log in. Without logging-in, you can't do much, so no.
If you want a more helpful answer, you'll have to be more precise: as in, why you can't use login.py, and what operations you do need to do with Pywikipedia.
One alternative that worked for me, when I wasn't able to interactively use my remote server (and thus not enter my password), was to copy my credentials to the remote server.
By default your remote permissions are stored in ~/.pywikibot/pywikibot.lwp, and it has worked for me in the past to log in locally, then copy this .lwp file to the remote server, and then I no longer had to enter my password on the remote server.
I don't claim this method to be secure at all, but it is a hack.
I'm looking at creating a server in python that I can run, and will work as an SSH server. This will then let different users login, and act as if they'd logged in normally, but only had access to one command.
I want to do this so that I can have a system where I can add users to without having to create a system wide account, so that they can then, for example, commit to a VCS branch, or similar.
While I can work out how to do this with conch to get it to a "custom" shell... I can't figure out how to make it so that the SSH stream works as if it were a real one (I'm preferably wanting to limit to /bin/bzr so that bzr+ssh will work.
It needs to be in python (which i can get to do the authorisation) but don't know how to do the linking to the app.
This needs to be in python to work within the app its designed for, and to be able to be used for those without access to add new users
When you write a Conch server, you can control what happens when the client makes a shell request by implementing ISession.openShell. The Conch server will request IConchUser from your realm and then adapt the resulting avatar to ISession to call openShell on it if necessary.
ISession.openShell's job is to take the transport object passed to it and associate it with a protocol to interpret the bytes received from it and, if desired, to write bytes to it to be sent to the client.
In an unfortunate twist, the object passed to openShell which represents the transport is actually an IProcessProtocol provider. This means that you need to call makeConnection on it, passing an IProcessTransport provider. When data is received from the client, the IProcessProtocol will call writeToChild on the transport you pass to makeConnection. When you want to send data to the client, you should call childDataReceived on it.
To see the exact behavior, I suggest reading the implementation of the IProcessProtocol that is passed in. Don't depend on anything that's not part of IProcessProtocol, but seeing the implementation can make it easier to understand what's going on.
You may also want to look at the implementation of the normal shell-creation to get a sense of what you're aiming for. This will give you a clue about how to associate the stdio of the bzr child process you launch with the SSH channel.
While Python really is my favorite language, I think you need not create you own server for this. When you look at the OpenSSH Manualpage for sshd you'll find the "command" options for the authorized keys file that lets you define a specific command to run on login.
Using keys, you can use one system account to allow many user to log in, just put their public keys in the account's authorized keys file.
We are using this to create SSH tunnels for SVN and it works just great.