So I tried adding R to the path on windows 10 (that is supposedly easy).
System Properties -> Environment variables -> Edit -> new: copy and paste: "C:\Program Files\R\R-3.5.0\bin\x64"
Now the thing is, Powershell just refuses to start the R environment when I type in R. R.exe works apparently. Rgui works as well. Is R a reserved letter in powershell or something? It also seems to repeat the previous command sometimes but that doesn't really seem completely consistent either.
(I put this entry on top of the list of the path and restarted the pc already)
when entering get-alias r I got the following result, so yes "r" is already taken ...
CommandType Name Version Source
----------- ---- ------- ------
Alias r -> Invoke-History
PS: you could remove that alias with remove-item alias:\r from your current powershell session and test if "r" then starts "R.exe". if that works for you, you could edit your profile to remove the alias "r -> Invoke-History" from every new session.
To generalize Guenther Schmitz' helpful answer:
PowerShell has several types of commands, whose precedence is:
Alias
Function
Cmdlet
External application
Note that name resolution is always case-insensitive, so that both r and R refer to the same command.
That is, before R resolves to R.exe, it is not only an r alias that could get in the way, but potentially also a function or a cmdlet (though the latter case is hypothetical, because well-behaved cmdlets follow a <Verb>-<Noun> naming pattern).
Note that built-in aliases shadowing external programs, especially standard ones, is problematic, and in the context of PowerShell Core a discussion is underway about whether to remove all built-in aliases and make them opt-in only - see this GitHub issue.
To see what a given name resolves to, use the Get-Command cmdlet:
# See what R resolves to
Get-Command R
# See ALL commands that R *can* resolve to, with the EFFECTIVE one listed first:
Get-Command -All R
Choices for unambiguously targeting R.exe:
(As you already know) If its folder is in one of the folders listed in environment variable $env:PATH, append .exe - i.e., use the filename extension explicitly:
R.exe ...
Use R.exe's full path (note the need for & for invocation, because the path needs quoting):
& "C:\Program Files\R\R-3.5.0\bin\x64\R.exe" ...
(For the sake of completeness; this is the cumbersome equivalent of using just R.exe): Use Get-Command -Type Application to locate the executable:
& (Get-Command -Type Application R) ...
Alternatively, as stated in Guenther's answer, you could add Remove-Alias r to your PowerShell $PROFILE file in order to remove the built-in alias on session startup, which then allows you to just use r to start R.exe.
Run the following code in your console to install the R package. This code will automatically add R to your os PATH.
sudo apt-get install littler
Related
I am aware that similar questions have been asked before, but I either don't understand the answers, or there aren't any; so I decided to describe my problem in as much detail as possible.
Problem:
RStudio reticulate package uses Python from this path:
"/usr/bin/python"
but I want it to use python from this path - always, as a default:
"/Library/Frameworks/Python.framework/Versions/3.7/bin/python3"
How do I know it happens?
I open RStudio, and create a new python script. A new file with an extension .py is generated. I type something in:
import pandas as pd
and execute (by clicking cmd+enter). I then see what happens in the console - the reticulate package is called:
reticulate::repl_python()
Python 2.7.10 (/usr/bin/python)
Reticulate 1.12 REPL -- A Python interpreter in R.
I would like to permanently change where the reticulate package looks for Python.
From the Terminal I know:
$ python --version
Python 3.7.3
which python3
/Library/Frameworks/Python.framework/Versions/3.7/bin/python3
So, I would like to tell RStudio to always look in this path to find Python 3.7. I have tried to use the following command, run from an R script:
use_python("/Library/Frameworks/Python.framework/Versions/3.7/bin/python3")
but it doesn't do anything - my naive understanding is that this command is useful within an R markdown file, i.e. when I have code that combines R and Python, in separate chunks. I would like to change the path that is used when a Python script is run from within RStudio. Is there some kind of a config file I could edit?
I hope this makes sense. I am not a regular Python user, only started learning now, and I am also not very good with paths, so I would appreciate step-by-step answers.
OK, so I have posted too early - after some more googling I can solve this problem myself, but I think it is worth posting an answer here for people like me (i.e. not path-proficient or python-proficient).
There is something like a config file for R, called .Renviron. In order to access it, use Terminal to go to your home directory (i.e. the one that you go to when you type 'cd'). If you have never used this file before, it might not exist, in which case you need to create it.
Once in your home directory, type:
ls -a
then check on the list of files that appears whether .Renviron is there. Below are instructions what if you already have .Renviron (IF YES), and what if you don't (IF NO).
IF NO, type:
touch .Renviron
which creates the file.
IF YES, just proceed as below (without using the touch command).
Write:
nano .Renviron
the .Renviron file will open. In it, add a line that says:
RETICULATE_PYTHON="enter your desired path here"
so, in my case, this is:
RETICULATE_PYTHON="/Library/Frameworks/Python.framework/Versions/3.7/bin/python3"
now save the file by exiting nano (ctrl+x) and clicking 'y' when it asks whether to save changes (press 'y' then press enter).
restart you RStudio. It should work now. I hope this is useful!
I recently found a fix for Python getpass not working on Windows: Python not working in the command line of git bash
Or at least that was the last thing I remember about changing my python configurations. (This is for Python 3.6.1 on Windows 10)
Now I also use Python to other tasks which simply has subprocess calls to type several commands on terminal:
go build ./folder/
mv ./src/ ./bin/
I get the error: go: GOPATH entry is relative; must be absolute: "/c/Users/OP/work". But I don't get it if I type go build ./src/folder myself.
I have GOPATH set to C:\work in Environment Variables. I have tried with a ;.
Is there a way to reverse the alias python every time? Or what is happening exactly when setting an alias for python to winpty?
I'm thinking that when I call go build directly, it is called by either my user profile or system. And when python's subprocess calls it, it calls the opposite. Therefore, I have two GOPATH variables even though I have only 1 set in environment variable.
Side Note: another recent change on GOPATH was changing it from C:/go because it couldn't be the same as GOROOT. That error popped up randomly for some reason. It worked with that setting for a while and I don't remember changing anything before except adding another import package on top of the many other ones already being used.
Update: with type python I get the result: python is aliased to 'winpty python.exe'. Therefore I tried to undo that with unalias python. The new result I get is: python is hashed (/c/Users/OP/AppData/Local/Programs/Python/Python36/python).
This fixed the go build command within Python's subprocess. However, that alias was a fix for another Python issue with using getpass package.
On top of my unalias python fix, I also discovered something interesting: when I change the environment variables for GOPATH from C:\work; to C:\go, all go commands still spit the error go: GOPATH entry is relative; must be absolute: "". I got this same error (but different path) from updating Windows 10 Fall Creators update. Maybe it is related.
Simply closing MINGW and reopening it fixed the issue. So perhaps it was saying a copy of my environment variables and using that as a reference instead of the actual system properties.
I know this is not a popular question, but someone could benefit from my hours of investigating and debugging.
Under Windows you must use a Windows style GOPATH like eg d:\code and probably you should use cmd shell and nothing else. Unfortunately cygwin paths (and probably others too) do no longer work especially for go get reaching out to git.
Stick to Windows paths and Windows shell.
The df command displays the amount of disk space occupied by mounted or unmounted file systems, the amount of used and available space, and how much of the file system's total capacity has been used.
Linux has df command in the following location /bin whereas in Solaris in the following location /usr/gnu/bin...
If suppose /usr/bin is set in the PATH, then programmatically, i need to ensure that one of required df (as mentioned above) is invoked instead of the user defined df.
One solution to this problem is using uname to get the OS and set the df accordingly... Is there any other better way to do this where i am not dependent on the OS.
Note: the default df and gnu df give different outputs hence i need to invoke the required df command on two different OS programmatically (the paths are mentioned above)
DID NOT FIND ANY SOLUTION TO THE PROBLEM
Used the alternative solution that i had provided in the question itself!
There is no "default" df on Solaris. You have various df commands, each one designed to suit specific needs.
/usr/bin/df is the one used by default by root and most users in Solaris 10 and older installations. This is the one used by all system scripts.
/usr/xpg4/bin/df is the POSIX compliant version used by people and scripts requiring standard compliance.
/usr/gnu/bin/df is the GNU version of df only available with Solaris 11 and newer, it appears first in non root users default PATH, but not on root default PATH.
Of course, users are free to change their PATH to have a specific df to appears first, or even a customized one not described here, a function, an alias, whatever.
If you want to write a portable script that doesn't rely on user or system customizations, you can run this command:
PATH=$(getconf PATH) df
If you want to use a specific df version that has its own extensions like GNU df, you need to prepend the directory where this command is located to the PATH variable.
Whenever you fire any command in any unix variant then it checks you PATH env variable. It check the command in each directory in the same sequence mentioned in PATH env variable.
So in you shell script just set PATH variable so that default df path will come at the beginning like below.
PATH = Defaut_df_path:$PATH
Whatever be the OS, if you fire "df" it will be your default "df".
System Admin Solution-
Please do this in .bashrc file ( or bash-profile) . Next time df will always trigger default df.
#!/usr/bin/sh
default_path='/usr/bin';
PATH=$default_path:$PATH;
echo $PATH;
df
which df ## this will give you path which you are using
Programming solution-
If you are writing some shell script then please do this before using df. It will set for that particular run.
I think in most linux varient df default location is /bin or /usr/bin. So setting these path are suffice. Also you can check if /bin/df exists then run /bin/df otherwise /usr/bin/df like below.
if [ -e /bin/df ]
then
/bin/df
else
/usr/bin/df
fi
From what I could gather you have two variants of 'df' in the solaris system. My suggestion: modify the environment variables before you start the process. Doing that with python's subprocess interface is quite easy.
solution 1
Try calling platform.uname() and check if the os is solaris or linux. I think the call returns a tuple about the operating system.
import subprocess, os , platform
if(os.platform()[0] == 'Solaris')
my_env = os.environ.copy()
my_env["PATH"] = "/usr/bin:" + my_env["PATH"]
subprocess.Popen(my_command, env=my_env)
subprocess.Popen(my_command, env=NONE)
solution 2
Since the call checks each entry in PATH one by one, prepend [X]( the path of df you like) to PATH. If its solaris it gets picked up otherwise it moves on to the next entry in PATH.
Are the target systems somehow under your control, and does this involve a limited set of servers?
If so, how about adding a soft link in both the Solaris and Linux servers, in the same location and with the same name?
Something like:
Solaris: ln -s /usr/gnu/bin/df /usr/bin/my_df
Linux: ln -s /bin/df /usr/bin/my_df
Then let your script use /usr/bin/my_df for every box.
Not fancy and rather simple approach... but maybe it would work for you?
Just my 2c.
The only solution top this problem seems using uname to get the OS and
set the df accordingly... same as what i had stated in the problem!!!
(Note: I’ve Linux in mind, but the problem may apply on other platforms.)
Problem: Linux doesn’t do suid on #! scripts nor does it activate “Linux capabilities” on them.
Why dow we have this problem? Because during the kernel interpreter setup to run the script, an attacker may have replaced that file. How? The formerly trusted suid/capability-enabled script file may be in a directory he has control over (e.g. can delete the not-owned trusted file, or the file is actually a symbolic link he owns).
Proper solution: make the kernel allow suid/cap scripts if: a) it is clear that the caller has no power over the script file -or- like a couple of other operating systems do b) pass the script as /dev/fd/x, referring to the originally kernel-opened trusted file.
Answer I’m looking for: for kernels which can’t do this (all Linux), I need a safe “now” solution.
What do I have in mind? A binary wrapper, which does what the kernel does not, in a safe way.
I would like to
hear from established wrappers for (Python) scripts that pass Linux capabilities and possibly suid from the script file to the interpreter to make them effective.
get comments on my wrapper proposed below
Problems with sudo: sudo is not a good wrapper, because it doesn’t help the kernel to not fall for that just explained “script got replaced” trap (“man sudo” under caveats says so).
Proposed wrapper
actually, I want a little program, which generates the wrapper
command line, e.g.: sudo suid_capability_wrapper ./script.py
script.py has already the suid bit and capabilites set (no function, just information)
the generator suid_capability_wrapper does
generate C(?) source and compile
compile output into: default: basename script.py .py, or argument -o
set the wrapper owner, group, suid like script.py
set the permitted capabilities like script.py, ignore inheritable and effective caps
warn if the interpreter (e.g. /usr/bin/python) does not have the corresponding caps in its inheritable set (this is a system limitation: there is no way to pass on capabilites without suid-root otherwise)
the generated code does:
check if file descriptors 0, 1 and 2 are open, abort otherwise (possibly add more checks for too crazy environment conditions)
if compiled-in target script is compiled-in with relative path, determine self’s location via /proc/self/exe
combine own path with relative path to the script to find it
check if target scripts owner, group, permissions, caps, suid are still like the original (compiled-in) [this is the only non-necessary safety-check I want to include: otherwise I trust that script]
set the set of inherited capabilities equal to the set of permitted capabilities
execve() the interpreter similar to how the kernel does, but use the script-path we know, and the environment we got (the script should take care of the environment)
A bunch of notes and warnings may be printed by suid_capability_wrapper to educate the user about:
make sure nobody can manipulate the script (e.g. world writable)
be aware that suid/capabilities come from the wrapper, nothing cares about suid/xattr mounts for the script file
the interpreter (python) is execve()ed, it will get a dirty environment from here
it will also get the rest of the standard process environment passed through it, which is ... ... ... (read man-pages for exec to begin with)
use #!/usr/bin/python -E to immunize the python interpreter from environment variables
clean the environment yourself in the script or be aware that there is a lot of code you run as side-effect which does care about some of these variables
You don't want to use a shebang at all, on any file - you want to use a binary which invokes the Python interpreter, then tells it to start the script file for which you asked.
It needs to do three things:
Start a Python interpreter (from a trusted path, breaking chroot jails and so on). I suggest statically linking libpython and using the CPython API for this, but it's up to you.
Open the script file FD and atomically check that it is both suid and owned by root. Don't allow the file to be altered between the check and the execution - be careful.
Tell CPython to execute the script from the FD you opened earlier.
This will give you a binary which will execute all owned-by-root-and-suid scripts under Python only. You only need one such program, not one per script. It's your "suidpythonrunner".
As you surmised, you must clear the environment before running Python. LD_LIBRARY_PATH is taken care of by the kernel, but PYTHONPATH could be deadly.
Okay, I'm having one of those moments that makes me question my ability to use a computer. This is not the sort of question I imagined asking as my first SO post, but here goes.
Started on Zed's new "Learn Python the Hard Way" since I've been looking to get back into programming after a 10 year hiatus and python was always what I wanted. This book has really spoken to me. That being said, I'm having a serious issue with pydoc from the command. I've got all the directories in c:/python26 in my system path and I can execute pydoc from the command line just fine regardless of pwd - but it accepts no arguments. Doesn't matter what I type, I just get the standard pydoc output telling me the acceptable arguments.
Any ideas? For what it's worth, I installed ActivePython as per Zed's suggestion.
C:\Users\Chevee>pydoc file
pydoc - the Python documentation tool
pydoc.py <name> ...
Show text documentation on something. <name> may be the name of a
Python keyword, topic, function, module, or package, or a dotted
reference to a class or function within a module or module in a
package. If <name> contains a '\', it is used as the path to a
Python source file to document. If name is 'keywords', 'topics',
or 'modules', a listing of these things is displayed.
pydoc.py -k <keyword>
Search for a keyword in the synopsis lines of all available modules.
pydoc.py -p <port>
Start an HTTP server on the given port on the local machine.
pydoc.py -g
Pop up a graphical interface for finding and serving documentation.
pydoc.py -w <name> ...
Write out the HTML documentation for a module to a file in the current
directory. If <name> contains a '\', it is treated as a filename; if
it names a directory, documentation is written for all the contents.
C:\Users\Chevee>
EDIT: New information, pydoc works just fine in PowerShell. As a linux user, I have no idea why I'm trying to use cmd anyways--but I'd still love to figure out what's up with pydoc and cmd.
EDIT 2: More new information. In cmd...
c:\>python c:/python26/lib/pydoc.py file
...works just fine. Everything works just fine with just pydoc in PowerShell without me worrying about pwd, or extensions or paths.
In Windows Powershell use: python -m pydoc
Examples:
python -m pydoc open
python -m pydoc raw_input
python -m pydoc argv
When you type the name of a file at the windows command prompt, cmd can check the windows registry for the default file association, and use that program to open it. So if the Inkscape installer associated .py files with its own version of python, cmd might preferentially run that and ignore the PATH entirely. See this question.
Based on your second edit, you may have more than one copy of pydoc.py in your path, with the 'wrong' one first such that when it starts up it doesn't have the correct environment in which to execute.
python -m pydoc -k/p/g/w <name>
Syntax for pydoc on windows:
alt1:
C:\path\PythonXX\python.exe C:\path\PythonXX\Lib\pydoc.py -k/p/g/w X:\path\file_to_doc.py
alt2:
python -m pydoc -k/p/g/w X:\path\file_to_doc.py
Of which the latter is the one to prefer, duh. However it requires your windows installation to have registered python to the environment variable "Path".
Setup windows environment variables:
Look at this site for a guide on where to find them. The one you'll be looking for is "Path". If you select Path and click Edit you will see a long row of paths pointing to different folders. The Path's you see here is what allows you to basically reach a veriety of programs in the command line by just entering the name of the program, instead of the whole path to it. So what you want to do here is to locate your Python installation and copy its full path like this: X:\subfolders\PythonXX\ Then you add it to the very end of the long row of Path's like this:
X:\earlier\path\to\something;X:\subfolders\PythonXX\
Notice the ";" that seperates the different paths, make sure not to forget it. When done, click to confirm/Ok, then you would need to restart any cmd.exe that's already open.
The pydoc.py
The thing is that pydoc is a module of the standard python lib, and it's also powered by python. The windows environment, of what I understand, requires you to specify with which program you want to run a certain file with. So to run the pydoc.py-file we would use:
Open file in windows cmd.exe:
X:\subfolders\Python27\python.exe X:\subfolders\Python27\Lib\pydoc.py
pydoc.py's arguments:
pydoc.py comes with a veriety of command line-based features that allows you to enter certain arguments:
-k/p/g/w of which will trigger different behaviours of the pydoc.py-program.
Send arguments to a program through command line:
The syntax to enter these arguments is of what I know always after the x:\pathtofile\filename.suffix, seperated by a simple space. Which gives us the final:
alt1:
X:\subfolders\Python27\python.exe X:\subfolders\Python27\Lib\pydoc.py -w X:\path\file_to_doc.py
alt2 (with python registered to path):
python -m pydoc -w X:\path\file_to_doc.py
The "w"-option will give you a HTML-documentation for the file you want to run documentation on. Notice that pydoc.py will (according to my tests) create the documentation-file in the current working directory. Meaning that you will need to place yourself in a folder of choice before you actually run the command.
The function of -m
Of what I can find, the -m seem to handle registry entries, atleast in the msiexec.exe. I guess it might be used for programs in general this way. So my speculative idea of it is that if "-m" is applied, the pursuing arguments paths will be rewritten so that the .exe-file will be used as a path-reference. But as said, rather speculative.
-m Rewrites all required computer-specific registry entries. (in msiexec.exe) According to Microsoft