Java PATH not set when creating a Azure Paas Role - azure

I am creating an Azure PaaS role which sets the PATH variable for java.exe .
I have a background task which does that.
The startupApp.cmd looks like
setx PATH %PATH%;%CD%\jdk\bin\ /m
cscript /NoLogo util\unzip.vbs jdk.zip "%CD%"
Call the bat file to start my application.
When the VM starts I see that the PATH environment variable is correctly set and points to where the jdk\bin folder. My application however fails to start with the error "java is not recognised as an internal or external batch command".
JAVA command to start my app is
java %JAVA_OPTS% %LOG_OPTS% %LOG4J_OPTS% -cp my_app.jar %MAIN_CLASS%
Here is the confusing path,
After I log into the VM and open a command prompt window and type java I see that it works fine.
If I restart the VM, the java command to bring up my app runs fine and I and my app too starts fine.

There is a significant difference between setx and set function:
set takes effect in local cmd context. Meaning once you exit or close the cmd window, you lose the environment variable.
setx takes effect in future cmd context. So you won't see the environment variable and its value in the current cmd. You need to open a new cmd window to see it.
If you want to use it global and immediate you should use both functions side by side.
Description taken from: http://batcheero.blogspot.de/2008/02/set-and-setx.html

Related

IIS - Setting the physical path of an Application with appcmd

In IIS, I have a web site "Default Web Site" with an application "test2". I want to set the physical path of that application to "E:\temp\out1". That directory already exists.
When I run this in Powershell (as an administrator):
appcmd.exe set app "Default Web Site/test2" -[path='/'].physicalpath:E:\temp\out1
I get this error message:
ERROR ( message:Malformed collection indexer; format is [#position,name='value',name2='value2',...]. The #position specifier is optional, and be '#start', '#end', or '#N' where N is a numeric index into the collection. )
I have no idea what that means.
Would very much appreciate a working example of using appcmd to set the physical path of an IIS application.
Turns out that the command in my question actually works on Command Prompt. However, I tried to run it from a Powershell prompt, and there I got the error message.
I couldn't find a way to run the command from Powershell. In the end, my solution was to write the command to a temporary .bat file, then execute that file from Powershell.
If I set my double quotes like this it works from Powershell prompt.
appcmd.exe set app "Default Web Site/test2" -"[path='/'].physicalpath:E:\temp\out1"

Azure Powershell - load variables from another script file

In Azure DevOps, I have an Azure Powershell task to create some resources using ps1 script in repo. This script working fine.
Now I need to split the script and variables into different files.
I created files SB-Config.ps1 for variables and ServiceBus.ps1 with main script. Moved all vars into SB-Config.ps1 .
Both files are in the same folder and in ServiceBus.ps1 I added:
. .\SB-Config.ps1
But Azure Devops fails with error:
What I'm doing wrong and how to get variables from SB-Config.ps1 script, when running ServiceBus.ps1 file?
I am able to reproduce your situation on my side.
Same issue as yours.
You can run this command to output the location of current work space:
Get-Location
I notice the powershell script file on your side is in the sub folder of Default working directory.
So do you set the work space in the powershell script file you are running first?
Set-Location $env:System_DefaultWorkingDirectory\subfolders
In your situation, I think the issue comes from the current work space is System_DefaultWorkingDirectory , the error output means the script can't get the file you want. This issue only occurs when you select 'file path' to run.

Why my program.exe (made in Python) can't use new environment variable after it restarted?

I am developing an executable with Python 3.7 on Windows 10.
My software needs to install 2 programs: the sdkmanager and the build-tools utilities.
My main issue is to use the environment variables freshly modified.
To install build-tools, I need first to install SDKmanager. When my code installs SDKManager, it is adding environment variables to make the program "sdkmanager.bat" available in the environment.
The first command my software is doing is "sdkmanager --list". When my program.exe run this command, it says "this program is not recognized and internal or external command". It is normal as my program.exe just changed the environment variable PATH and it needs to restart to use it.
So my program.exe start a new instance of program.exe. This 2nd program.exe detect the first program.exe and kill it in order to let only 1 program.exe running.
So this 2nd program.exe suppose to enjoy the new environment variable, but it is not the case.
I tried all the possible code to start new porgram.exe:
proc = subprocess.Popen("start myprogram.exe", shell=True,stdin=None, stdout=True, stderr=None, close_fds=True)
os.system('start cmd /c "myprogram.exe"')
proc = os.popen("start cmd /c myprogram.exe")
proc = subprocess.check_call(['myprogram.exe'], shell=True)
proc = subprocess.run(['myprogram.exe'])
ctypes.windll.shell32.ShellExecuteW(None, "runas", 'myprogram.exe', '', None, 1)
etc....
It didn't work. Each time my program can't run the command "sdkmanager --list" as it says "this program is not recognized and internal or external command".
What is weird is I am displaying the value of the environment variable PATH and I can see the path to the script sdkmanager.bat.
So I used different methods to propagate the new environment variables:
#Method 1
def RefreshEnvironment():
#https://gist.github.com/apetrone/5937002
HWND_BROADCAST = 0xFFFF
WM_SETTINGCHANGE = 0x001A
SMTO_ABORTIFHUNG = 0x0002
sParam = "Environment"
res1, res2 = win32gui.SendMessageTimeout( HWND_BROADCAST, WM_SETTINGCHANGE, 0, sParam, SMTO_ABORTIFHUNG, 100 )
bool_res=bool(res1)
if not res1:
logger.info(f"result: {bool_res} {res2} from SendMessageTimeout")
#Method 2
def RefreshEnvironment(timeout_ms=2000):
#https://programtalk.com/python-examples-amp/win32con.HWND_BROADCAST/
"""Broadcast a message to all top-level windows informing them that
an environment change has occurred. The message must be sent, not posted,
and times out after `timeout_ms` ms since some top-level windows handle this
badly. NB This is a static method.
"""
win32gui.SendMessageTimeout(
win32con.HWND_BROADCAST, win32con.WM_SETTINGCHANGE,
0, "Environment",
win32con.SMTO_ABORTIFHUNG, timeout_ms
)
But it didn't work.
What is very weird, is when I restart program.exe manually myself by double clicking on it, it works! program.exe recognized the command "sdkmanager --list" when I run the program myself whereas it doesn't if program.exe restart itself. I don't understand.
Does anyone already face this situation where your program has to restart to enjoy the environment variable?
My problem is I didn't understand well how the environment works with python.
In fact, there are 2 environments:
The environment of the machine.
The environment of python loaded when Python starts.
I was changing with success the environment of my machine, but Python was keeping its own environment in its memory. So even if everything was updated in the environment machine, Python was ignoring it, even after restarting the program.
I had to use the module os.environ to load my new environment variable in the Python environment in order to let Python enjoy these new environment variables.
Here is the code I use now which is working from my side:
# After I change the environment variable, I use my function 'GetEnvVarSys' to get the environment variable from Windows registry
ANDROID_HOME=GetEnvVarSys("ANDROID_HOME")
JAVA_HOME=GetEnvVarSys("JAVA_HOME")
PATH=GetEnvVarSys("PATH")
# then I pass them to Python os.environment
os.environ['ANDROID_HOME'] = ANDROID_HOME
os.environ['JAVA_HOME'] = JAVA_HOME
os.environ['PATH'] = PATH

Property env is not allowed in launch.json [VSCode]

All I've done is initialize a template Azure Functions project in VS and when I try to set run configuration environment variables via launch.json, VS directly warns me that it's not "allowed".
Furthermore, even when I try to run my .ps1 with env anyway, it doesn't work because I have something like
$variable = $env:AWS_REGION
Write-Host $variable
and the terminal output is blank, so clearly it's not working.
It's not possible directly atm see Issue 1472
I can however see that you are trying to start local version of azure functions, so you could declare your environment variables in local.settings.json or in profile.ps1
Edit: This just means its avalible while running the local instance of az functions, and not avalible in the integrated powershell console. the local.settings.json is also the local version of app configuration in azure and you should makre sure to include this file in your gitignore, if you are using git.

Dotnet Core - Get the application's launch path

Question - Is there a better/right way to get the application's launch path?
Setup -
I have a console application that runs in a Linux Debian docker image. I am building the application using the --runtime linux-x64 command line switch and have all the runtime identifiers set appropriately. I was expecting the application to behave the same whether launching it by calling dotnet MyApplication.dll or ./MyApplication but they are not.
Culprit Code -
I have deployed files in a folder below the application directory that I reference so I do the following to get what I consider my launch path. I have read various articles saying this is the correct way to get what I want, and it works depending on how I launch it.
using var processModule = Process.GetCurrentProcess().MainModule;
var basePath = Path.GetDirectoryName(processModule?.FileName);
When launching this using the comand dotnet MyApplication.dll the above codes path is /usr/share/dotnet
When launching this using the command ./MyApplication.dll the path is then /app
I understand why using dotnet would be different as it is the process that is running my code, but again it was unexpected.
Any help here to what I should use given the current environment would be appreciated. Ultimately I need the path where the console application started from as gathered by the application when it starts up.
Thanks for your help.
This code should work:
public static IConfiguration LoadConfiguration()
{
var assemblyDirectory = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
.....
}

Resources