Current working directory for SXPG_COMMAND_EXECUTE? - command-line

Is there a way to specify the current working directory for the system command executed by the function module SXPG_COMMAND_EXECUTE?
I do not see any parameter which would allow me to do that either by defining the command in transaction SM69 or on the list of IMPORTING parameters in SE37.
It looks like by default such commands are started in DIR_HOME which can be viewed by the transaction AL11. Do I have any control over that?

There isn't a way of doing it via `SM69' unfortunately. I think the only solution is to create a script and call that.
I was going to suggest wrapping the statements in a SM69 command defined as a call to sh with parameters of -c 'cd <dir> && /path/to/command' but unfortunately that doesn't work. According to note 401095 wildcards are not permitted. When I tested, && was translated into a single &, causing the command to fail.

Would be good if you access this information using FM FILE_GET_NAME_USING_PATH (export the script name for which you want to find the physical directory).
The recieving path can be used in SXPG_COMMAND_EXECUTE.

Because the external commands I called were actually .bat files I solved this by putting the following expression at the beginning of each and every one.
cd /d %~dp0
This Stackoverflow question helped a lot actually.

Related

List directories of different location in fish tab-completion

I would like to create a fish function that acts as a shortcut into a directory.
The function looks like this:
function mydir -d "Navigate to mydir and its subdirectories from anywhere"
cd $HOME/some/path/mydir/$argv
end
The function works well, but I would like to add tab-completion. I currently have this for tab-completion:
complete --no-files --exclusive --command mydir --arguments "(__fish_complete_directories)"
The problem is that this will tab-complete to the directories in the current working directory. I would instead like it to tab-complete to the directories in $HOME/some/path/mydir/. I cannot find an example or flag in the documentation that would help me do this.
I do not know fish very well, but I thought one way to do this would be to manually loop over those directories and add them as options, but it doesn't feel right and I am struggling with that implementation anyway.
Honestly, your "looping over those directories" seems like the most "fish-like" way to me, but given that someone has already gone through the trouble of creating and debugging the existing __fish_complete_directories (Github link), I think I'd just use it as a starting point for your own completion function.
It seems to me that you could just add a pushd $HOME/some/path/mydir before the "non-existent command hack" and then popd at the end.

Properly referencing scripts in PowerShell

I'm a newbie in PowerShell and I'm having some problems when defining some utility scripts that are "included" in other files; the problem is regarding paths. Let me explain the issue with a simple example:
Imagine you have some utility script named utility.ps1 located under /tools and you want to invoke it from a build.ps1 placed under /build. Now imagine that the utility.ps1 invokes some other utility script in the same folder called "utility2.ps1". So,
utility.ps1:
[...]
.".\utility2.ps1"
[...]
build.ps1:
[...]
."..\tools\utility.ps1"
[...]
The problem here is that when calling from build to utility.ps1 and then from this last one to utility2.ps1, powershell is trying to load utility2.ps1 from the current dir (build) instead of the tools dir.
My current workaround is pushd . before calling and popd after that but it smells bad, I know; on the other hand if some day I move scripts to some other location I'd need to update all my scripts that use the moved one... a mess.
So, I'm doing something very wrong; what would be the proper one to do this, making the client script unaware and independant of the "utility" script location?
The answer by PetSerAl in the comments is perfect but will work for PowerShell 3+. If for some reason you want your script to be backward compatible as well, then use the below code snippet to find the $ScriptRootPath (which is automatically populated via $PSScriptRoot for PS 3+)
$ScriptRootPath = Split-Path $MyInvocation.MyCommand.Path -Parent
For PS 3+, populate this variable via the global variable:
$ScriptRootPath = $PSScriptRoot
and then use the solution as described by PetSerAl,
i.e. for utility.ps1: . "$ScriptRootPath\utility2.ps1"
for build.ps1: . "$ScriptRootPath\..\tools\utility.ps1"
Also refer this question on SO

export PATH creating a redundant path

I need to add some perl scripts to PATH, but when I do, and try to run the scripts, it can't find the files. For some reason it is using a redundant path and doesn't find it. I dont know how to describe the problem but the code is pretty self-explanatory.
[lsk250#murphy portfolio-handout]$ pwd
/home/lsk250/portfolio-handout
[lsk250#murphy portfolio-handout]$ export PATH=$PATH:/home/lsk250/portfolio-handout/
[lsk250#murphy portfolio-handout]$ time_series_symbol_project.pl
env: /home/lsk250/portfolio-handout//home/lsk250/portfolio-handout/get_data.pl: No such file or directory
sh: line 1: 17758 Aborted (core dumped) time_series_project _data.in 8 AWAIT 300 ARIMA 2 1 2 2> /dev/null
Any ideas whats the right export command I should use to get this right?
There is nothing wrong in how you export PATH variable except that you may already have your "pwd" there.
As far as I can see the get_data.pl is called from time_series_symbol_project.pl (or from some other script called from time_series_symbol_project.pl and so on) and I would check how it is called.
Perhaps you could also see if PATH is changed somewhere in your scripts.
i'm guessing the "shebang" line (#!) and/or file permissions on 'get_data.pl' is incorrect.

finding a files path in the command line

I am doing a batch scripting assignment where I have to call one script from inside another. I need the script to run the second script no matter where my lecturer saves these scripts. How would I do this. Is there some way to find the path of script inside the script and use that to execute the file. Any help would be great. I think I need to use %'s but i'm not sure.
The name of the script is Hello World.bat.
How would I copy Hello World.bat to the C:\ if I don't know which directory the lecturer has placed it in. what command/s would I use so that the copy would work regardless of the scripts location.
I don't see the "DOS" tag, but I'll assume that it is for now. If you want the entire path, you can get it by doing this:
echo %cd%
If you want just the last folder, this works (inside a .bat file):
for %%* in (.) do #echo %%~n*
Note that from the command line, the above command will work with single %'s:
for %* in (.) do #echo %~n*
If the script you are executing is calling other scripts in the SAME folder location, you can prefix the path statement with "%~dp0" or "%~dps0" but do not put a backslash between that and the name of the script you are calling. In other words, if script1.bat is calling script2.bat in the same folder, the statement in script1.bat would refer to "%~dp0script2.bat"
sorry about batch files, am not familiar, but in nix shell, there is the locate command which can return the path of the file , if you know the filename exactly and the name is unique.
like
name=$(locate filname)

How do I copy from numerous release directories to a single folder

Okay this is and isn't programming related I guess...
I've got a whole bunch of little useful console utilities scattered across a suite of projects that I wrote and I want to dump them all to a single directory to make using them simpler. The only issue is that I have them all compiled in both Debug and Release mode.
Given that I only want the release mode versions in my utilities directory, what switch would allow me to specify that I want all executables from my tree structure but only from within Release folders:
Example:
Projects\
Project1\
Bin\
Debug\
Project1.exe
Release\
Project1.exe
Project2\
etc etc...
To
Utilities\
Project1.exe
Project2.exe
Project3.exe
Project4.exe
...
etc etc...
I figured this would be a cinch with XCopy - but it doesn't seem to allow me to exclude the Debug directories - or rather - only include items in my Release directories.
Any ideas?
You can restrict it to only release executables with the following. However, I do not believe the other requirement of flattening is possible using xcopy alone. To do the restriction:
First create a file such as exclude.txt and put this inside:
\Debug\
Then use the following command:
xcopy /e /EXCLUDE:exclude.txt *.exe C:\target
You can, however, accomplish what you want using xxcopy (free for non-commercial use). Read technical bulletin #16 for an explanation of the flattening features.
If the claim in that technical bulletin is correct, then it confirms that flattening cannot be accomplished with xcopy alone.
The following command will do exactly what you want using xxcopy:
xxcopy /sgfo /X:*\Debug\* .\Projects\*.exe .\Utilities
I recommend reading the technical bulletin, however, as it gives more sophisticated options for the flattening. I chose one of the most basic above.
Sorry, I haven't tried it yet, but shouldn't you be using:
xcopy release*.exe d:\destination /s
I am currently on my Mac so, I cant really check to be for sure.
This might not help you with assembling them all in one place now, but going forward have you considered adding a post-build event to the projects in Visual Studio (I'm assuming you are using it based on the directory names)
xcopy /Y /I /E "$(TargetDir)\$(TargetFileName)" "c:\somedirectory\$(TargetFileName)"
Ok, this is probably not going to work for you since you seem to be on a windows machine.
Here goes anyway, for the logic.
# From the base directory
mkdir Utilities
find . -type f | grep -w Release > utils.txt
for f in $(<utils.txt); do cp $f Utilities/; done
You can combine the find and cp lines into one, I split them for readability.
To do this on a windows machine you'll need Cygwin or some such Unix Utilities handy.
Maybe there are tools in the Windows shell to do this...
This may help get you started:
C:\>for %i in (*) do dir "%~dpi\*.exe"
Used in the dir command as a modifier to i, ~dp uses the drive and path of everything found in (*). If I run the above in a folder that has several subfolders containing executables, I get a dir list of all of the executables in each folder.
You should be able to modify that to add '\bin\release\' following the ~dpi portion and change dir to xcopy. A little experimentation should make it pretty easy.
To use the for statement above in a batch file, change '%' to '%%' in both places.