I have to create windows container image with our application installed. Our application is a legacy one and it uses hostname in several places during installation. The docker build command doesnot have an option to pass the hostname. So, we are currently stuck at a point where when we run a container with the image created, our application fails to run as its expecting the hostname to be the generated name during the image creation time and not the one we pass with docker run command.
I tried to change the hostname within the container before installing our application using suggestions in this query.But,it did not work.
I wanted to understand if there is a way we can change the hostname from within the windows container?
The following worked for me -
rename-computer.ps1:
$ComputerName = "New Name"
Remove-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" -name "Hostname"
Remove-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" -name "NV Hostname"
Set-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Control\Computername\Computername" -name "Computername" -value $ComputerName
Set-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Control\Computername\ActiveComputername" -name "Computername" -value $ComputerName
Set-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" -name "Hostname" -value $ComputerName
Set-ItemProperty -path "HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters" -name "NV Hostname" -value $ComputerName
Set-ItemProperty -path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -name "AltDefaultDomainName" -value $ComputerName
Set-ItemProperty -path "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon" -name "DefaultDomainName" -value $ComputerName
Dockerfile:
COPY "rename-computer.ps1" "C:/"
RUN powershell -command "Set-ExecutionPolicy RemoteSigned" \
&& powershell -command "C:/rename-computer.ps1 ; hostname" \
&& powershell -command "Set-ExecutionPolicy Restricted" \
&& <your installer runs here>
Sources -
https://serverfault.com/a/731832/845133
https://gist.github.com/timnew/2373475
Related
For my projects I sometimes need to unittest my code against a ms sql server.
At the moment, I created a monstrous docker image, containing all the tools I need, including the sql server.
Now this image got to about 15 GB in size, which is really not cool.
So I'm trying to use the GitLab CICD Service part (as described here https://docs.gitlab.com/ee/ci/services/index.html).
But when I'm trying to add my (custom) image as a service I keep getting the health check issue:
*** WARNING: Service runner-hrtjgacu-project-1489-concurrent-0-2ae3f3cd2099f19a-gitlab.mydomain.lcaol__windowsdockerimages__mssql-0 probably didn't start properly.
Health check error:
service "runner-hrtjgacu-project-1489-concurrent-0-2ae3f3cd2099f19a-gitlab.mydomain.local__windowsdockerimages__mssql-0-wait-for-service" health check: exit code 1
Health check container logs:
2023-01-19T09:58:09.913696500Z FATAL: No HOST or PORT found
Service container logs:
*********
Now I found something online about needing to expose the ports of the service in the Dockerfile, so I tried that, but that did not help.
This is what my MSSQL DockerFile currently looks like:
FROM mcr.microsoft.com/windows/servercore:ltsc2019
# Download Links:
ENV exe "https://go.microsoft.com/fwlink/?linkid=840945"
ENV box "https://go.microsoft.com/fwlink/?linkid=840944"
ENV sa_password="_" \
attach_dbs="[]" \
ACCEPT_EULA="Y" \
sa_password_path="C:\ProgramData\Docker\secrets\sa-password"
SHELL ["powershell", "-Command", "$ErrorActionPreference = 'Stop'; $ProgressPreference = 'SilentlyContinue';"]
# make install files accessible
COPY start.ps1 /
WORKDIR /
RUN Invoke-WebRequest -Uri $env:box -OutFile SQL.box ; \
Invoke-WebRequest -Uri $env:exe -OutFile SQL.exe ; \
Start-Process -Wait -FilePath .\SQL.exe -ArgumentList /qs, /x:setup ; \
.\setup\setup.exe /q /ACTION=Install /INSTANCENAME=MSSQLSERVER /FEATURES=SQLEngine /UPDATEENABLED=0 /SQLSVCACCOUNT='NT AUTHORITY\System' /SQLSYSADMINACCOUNTS='BUILTIN\ADMINISTRATORS' /TCPENABLED=1 /NPENABLED=0 /IACCEPTSQLSERVERLICENSETERMS ; \
Remove-Item -Recurse -Force SQL.exe, SQL.box, setup
RUN stop-service MSSQLSERVER ; \
set-itemproperty -path 'HKLM:\software\microsoft\microsoft sql server\mssql14.MSSQLSERVER\mssqlserver\supersocketnetlib\tcp\ipall' -name tcpdynamicports -value '' ; \
set-itemproperty -path 'HKLM:\software\microsoft\microsoft sql server\mssql14.MSSQLSERVER\mssqlserver\supersocketnetlib\tcp\ipall' -name tcpport -value 1433 ; \
set-itemproperty -path 'HKLM:\software\microsoft\microsoft sql server\mssql14.MSSQLSERVER\mssqlserver\' -name LoginMode -value 2 ;
HEALTHCHECK CMD [ "sqlcmd", "-Q", "select 1" ]
EXPOSE 1433/tcp
EXPOSE 4022/tcp
EXPOSE 135/tcp
EXPOSE 1434/tcp
EXPOSE 1434/udp
CMD .\start -sa_password $env:sa_password -ACCEPT_EULA $env:ACCEPT_EULA -attach_dbs \"$env:attach_dbs\" -Verbose
And this is is my .gitlab-ci.yml file:
default:
image:
name: gitlab.mydomain.local:4567/windowsdockerimages/basicnetframeworkimage:latest
tags:
- windows
- docker
# The stages during this build
stages:
- build
build:
stage: build
script:
- echo "Hello world"
- ping mssql
- dotnet run
services:
- name: gitlab.mydomain.local:4567/windowsdockerimages/mssql
alias: mssql
Anyone who can help me get closer to the solution?
*Note, the ping mssql also fails, the container in which we run cannot find the DNS
entry
I would use an existing official image for MSSQL server (https://hub.docker.com/_/microsoft-mssql-server) and run unit tests in one container and the database in another one.
For my use case, I need to create a windows container of Activeperl application. I found a GitHub link which explains the process for a Strawberry Perl.
Code snippet from the link
RUN \
if(!(Test-Path -Path 'C:\Temp')) \
{ \
New-Item \
-Path 'C:\Temp' \
-ItemType Directory \
-Verbose | Out-Null ; \
} ; \
\
Invoke-WebRequest \
-Uri "http://strawberryperl.com/download/$ENV:PERL_VERSION/strawberry-perl-$ENV:PERL_VERSION-64bit.zip" \
-OutFile "C:\\Temp\\strawberry-perl-$ENV:PERL_VERSION-64bit.zip" \
-UseBasicParsing \
-Verbose ; \
\
Expand-Archive \
-Path "C:\\Temp\\strawberry-perl-$ENV:PERL_VERSION-64bit.zip" \
-DestinationPath 'C:\Program Files\Perl' \
-Verbose ; \
\
Set-ItemProperty \
-Path 'HKLM:\\SYSTEM\\CurrentControlSet\\Control\\Session Manager\\Environment' \
-Name 'Path' \
-Value $($ENV:Path + ';C:\Program Files\Perl\perl\bin;C:\Program Files\Perl\perl\site\bin;C:\Program Files\Perl\c\bin') \
-Verbose ;
Strawberryperl Uri - http://strawberryperl.com/download/$ENV:PERL_VERSION/strawberry-perl-$ENV:PERL_VERSION-64bit.zip
For me, I want an equivalent Uri for downloading Activeperl instead of Strawberryperl. I am even ok with a Windows Container Image with activeperl installed already. I just couldn't find any of them.
Since ActivePerl doesn't provide an option for downloading a zipped version of Perl.
This is how I was able to transfer an active Perl to a Windows container
In my host windows machine, I have downloaded the Active Perl from https://activeperl.software.informer.com/download/
The downloaded file is ActivePerl-5.28.1.0000-MSWin32-x64-e90bcbf1.msi
I have installed this at the location C:\Perl64\
Copied this Perl64 folder into a new folder called Perl_root, so that this can be copied into the container via Dockerfile. Create a file called Dockerfile in the same location as Perl_root.
Filesystem_Root
C:\
|__ docker_trial
|___ Perl_root
|___ Dockerfile
Dockerfile:
#pulled a windows container from docker hub
FROM mcr.microsoft.com/windows/servercore:1607-amd64
ADD Perl_root .
Open a command prompt and navigate to the folder where dockerfile is present.
>docker build --tag dockertrail:1.0 .
>docker run -it --name tag1 dockertrail:1.0
Once the terminal inside the docker container opens up, open a PowerShell and create the update the environment variable Path as below
Powershell>[Environment]::SetEnvironmentVariable("Path",$env:Path+"C:\Perl64\site\bin;C:\Perl64\bin","Machine")
exit from the PowerShell and container. Now restart the container tag1, for the environment variable to work.
start the container tag1 again, once it starts, open up a PowerShell and run the command $env:Path you must be able to see the perl path being added to environment variables.
Now check the functioning of Perl using the command perl -v
This should print the perl verion.
Trying to update IIS authentication settings using Powershell.
Here's the dockerfile:
FROM microsoft/aspnet
SHELL ["powershell"]
WORKDIR C:\MyWebApp
RUN Import-Module WebAdministration; `
New-WebApplication -Name 'MyWebApp' -Site 'Default Web Site' -PhysicalPath C:\MyWebApp -ApplicationPool DefaultAppPool; `
Set-WebConfigurationProperty -Filter "/system.webServer/security/authentication/anonymousAuthentication" -Name Enabled -Value False -PSPath IIS:\ -Location "'Default Web Site/MyWebApp'"; `
Set-WebConfigurationProperty -Filter "/system.webServer/security/authentication/basicAuthentication" -Name Enabled -Value False -PSPath IIS:\ -Location "'Default Web Site/MyWebApp'"; `
Set-WebConfigurationProperty -Filter "/system.webServer/security/authentication/windowsAuthentication" -Name Enabled -Value True -PSPath IIS:\ -Location "'Default Web Site/MyWebApp'"; `
Set-WebConfigurationProperty -Filter "/system.web/identity" -Name impersonate -Value True -PSPath IIS:\ -Location "'Default Web Site/MyWebApp'"; `
Set-ItemProperty -Path IIS:\AppPools\DefaultAppPool\ -Name managedPipelineMode -Value 0; `
Set-ItemProperty -Path IIS:\AppPools\DefaultAppPool\ -Name enable32BitAppOnWin64 -Value True;
Set-WebConfigurationProperty is causing W3SVC to get stopped and container exits.
PS C:\Projects\docker_workspace\app> docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS
96bc3c60e9df wcpapp:v1 "C:\\ServiceMonitor.e…" About a minute ago Exited (2147500037) 12 seconds ago
PS C:\Projects\docker_workspace\app> docker logs 96
Service 'w3svc' has been stopped
ERROR: Failed to start or query status of service 'w3svc' error [80004005]
Service 'w3svc' has been stopped
If I remove Set-WebConfigurationProperty statements, Container stays up and running. What am I missing here?
i have a windows application which I want to containerize. Its a windows desktop application (not web application). I did some searching and found very little about containerizing desktop application. The application which I want to containerize works fine on WindowsServerCore. I have Windowsservercore image on my machine.
I want to know how can I go about containerizing it. Any documentation or useful videos are available?
when i completed dockerfile can i interact with my application gui??? how???
You can find tons of example of WindowsServiceCore-based applications in StefanScherer/dockerfiles-windows
You need to write a Dockerfile (like for instance diskspd/Dockerfile where you copy/unzip/install the application you need.
FROM microsoft/windowsservercore:10.0.14393.1770
SHELL ["powershell", "-Command", "$ErrorActionPreference = 'Stop'; $ProgressPreference = 'SilentlyContinue';"]
ENV DISKSPD_VERSION 2.0.17
RUN Invoke-WebRequest $('https://gallery.technet.microsoft.com/DiskSpd-a-robust-storage-6cd2f223/file/152702/1/Diskspd-v{0}.zip' -f $env:DISKSPD_VERSION) -OutFile 'diskspd.zip' -UseBasicParsing ; \
Expand-Archive diskspd.zip -DestinationPath C:\ ; \
Remove-Item -Path diskspd.zip ; \
Remove-Item -Recurse armfre ; \
Remove-Item -Recurse x86fre ; \
Remove-Item *.docx ; \
Remove-Item *.pdf
ENTRYPOINT [ "C:\\amd64fre\\diskspd.exe" ]
That being said, a full GUI support for windowscoreserver is still requested:
"Create base container with full GUI support".
How do I add a D: drive to the microsoft/windowsservercore base image?
My Windows Server 2016 server has a D: drive. The server is an AWS instance.
This is with native Docker installed and not the "Docker for Windows" that has been around for a while.
We got it to work. Essentially, we're adding a symbolic link in the registry.
Add this to the dockerfile:
RUN powershell -NoProfile -Command \
New-Item -ItemType directory -Path C:\drived ; \
New-ItemProperty -Path 'HKLM:\SYSTEM\CurrentControlSet\Control\Session Manager\DOS Devices' -Name 'D:' -Value '\??\C:\drived' -PropertyType String;
I did this using the subst command:
mkdir c:\drived
subst d: c:\drived
I think such a drive is only visible in the current session, so it wouldn't work if you are using Windows services.