New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Upload MSI / Win32Lob apps #10
Comments
Sorry for the delayed response, it has been a particularly busy month! I am looking into this, and will get back to you soon. |
I've done some digging, and it looks like the Win32 app type is still in beta - this is why the script provided in the Scenario Modules (mentioned in the docs) does not work with Win32 apps. In order to make that script work with Win32 apps, you would need to:
Step 1 - Replace all calls to SDK cmdlets with Invoke-MSGraphRequestFor example, in the # Post the app metadata to Intune
$createdApp = $mobileApp | New-DeviceAppManagement_MobileApps into this: # Post the app metadata to Intune
$createdApp = Invoke-MSGraph `
-HttpMethod POST `
-Url 'deviceAppManagement/mobileApps' `
-Content $mobileApp Essentially, any cmdlet call where the noun starts with Step 2 - Manually construct the
|
Thanks for that Rohi. Im currently using this I tried ti create this function function Upload-Win32Lob(){
[cmdletbinding()]
param
(
[parameter(Mandatory=$true,Position=1)]
[ValidateNotNullOrEmpty()]
[string]$IntuneWinLocaton
)
$list = Get-ChildItem $IntuneWinLocaton -Filter *.intunewin
foreach ($item in $list)
{
try {
$LOBType = "microsoft.graph.win32LobApp"
if(Test-SourceFile ($IntuneWinLocaton + "\" + $item.json)){
Write-Host "JSON file doesn't exist..." -ForegroundColor Red
Write-Host "Script can't continue..." -ForegroundColor Red
Write-Host
break}
#Test-SourceFile ($IntuneWinLocaton + "\" + $item.json)
$Win32Path = ($IntuneWinLocaton + "\" + $item.name)
# Creating temp file name from Source File path
$tempFile = [System.IO.Path]::GetDirectoryName("$Win32Path") + "\" + [System.IO.Path]::GetFileNameWithoutExtension("$Win32Path") + "_temp.bin"
$json = [System.IO.Path]::GetDirectoryName("$Win32Path") + "\" + [System.IO.Path]::GetFileNameWithoutExtension("$Win32Path") + ".json"
Write-Host
Write-Host "Creating JSON data to pass to the service..." -ForegroundColor Yellow
$FileName = [System.IO.Path]::GetFileName("$Win32Path")
$JSON_Data = Get-Content $json
$JSON_Convert = $JSON_Data | ConvertFrom-Json
$JSON_Output = $JSON_Convert | ConvertTo-Json
Write-Host
Write-Host "Creating application in Intune..." -ForegroundColor Yellow
$mobileApp = MakePostRequest "mobileApps" $JSON_Output;
# Get the content version for the new app (this will always be 1 until the new app is committed).
Write-Host
Write-Host "Creating Content Version in the service for the application..." -ForegroundColor Yellow
$appId = $mobileApp.id;
$contentVersionUri = "mobileApps/$appId/$LOBType/contentVersions";
$contentVersion = MakePostRequest $contentVersionUri "{}";
# Encrypt file and Get File Information
Write-Host
Write-Host "Ecrypting the file '$Win32Path '..." -ForegroundColor Yellow
$encryptionInfo = EncryptFile $Win32Path $tempFile;
$Size = (Get-Item "$Win32Path").Length
$EncrySize = (Get-Item "$tempFile").Length
# Create a new file for the app.
Write-Host
Write-Host "Creating a new file entry in Azure for the upload..." -ForegroundColor Yellow
$contentVersionId = $contentVersion.id;
$fileBody = GetWin32FileBody "$FileName" $Size $EncrySize;
$filesUri = "mobileApps/$appId/$LOBType/contentVersions/$contentVersionId/files";
$file = MakePostRequest $filesUri ($fileBody | ConvertTo-Json);
# Wait for the service to process the new file request.
Write-Host
Write-Host "Waiting for the file entry URI to be created..." -ForegroundColor Yellow
$fileId = $file.id;
$fileUri = "mobileApps/$appId/$LOBType/contentVersions/$contentVersionId/files/$fileId";
$file = WaitForFileProcessing $fileUri "AzureStorageUriRequest";
# Upload the content to Azure Storage.
Write-Host
Write-Host "Uploading file to Azure Storage..." -f Yellow
$sasUri = $file.azureStorageUri;
UploadFileToAzureStorage $file.azureStorageUri $tempFile;
# Commit the file.
Write-Host
Write-Host "Committing the file into Azure Storage..." -ForegroundColor Yellow
$commitFileUri = "mobileApps/$appId/$LOBType/contentVersions/$contentVersionId/files/$fileId/commit";
MakePostRequest $commitFileUri ($encryptionInfo | ConvertTo-Json);
# Wait for the service to process the commit file request.
Write-Host
Write-Host "Waiting for the service to process the commit file request..." -ForegroundColor Yellow
$file = WaitForFileProcessing $fileUri "CommitFile";
# Commit the app.
Write-Host
Write-Host "Committing the file into Azure Storage..." -ForegroundColor Yellow
$commitAppUri = "mobileApps/$appId";
$commitAppBody = GetAppCommitBody $contentVersionId $LOBType;
MakePatchRequest $commitAppUri ($commitAppBody | ConvertTo-Json);
Write-Host "Removing Temporary file '$tempFile'..." -f Gray
Remove-Item -Path "$tempFile" -Force
Write-Host
Write-Host "Sleeping for $sleep seconds to allow patch completion..." -f Magenta
Start-Sleep $sleep
Write-Host
}
catch {
Write-Host "";
Write-Host -ForegroundColor Red "Aborting with exception: $($_.Exception.ToString())";
}
}
} It does create upload inserts the json with all the correct functions but never installs. Im not sure which component is failing but if i re-use the same app and re-upload the .intunewin everything works. i think once is compressing and creating the .bin file something that does work for when using MSI's doesnt when using intunewin files. |
I actually learned recently that uploading a win32 app works a little bit differently to other app types. Given this, I think you're doing the right thing by using the samples. Since this is off-topic for this repository, I would suggest opening an issue in the Intune PowerShell Samples GitHub repository that you downloaded this script from: https://github.com/microsoftgraph/powershell-intune-samples/issues. I will close this issue for now, but please feel free to re-open it (or create a new issue) if you have more questions about the Intune PowerShell SDK. |
Well its not, to be honest i'd expect that to be part of the Intune official SDK since its an option (eve thoug still in preview) to do it via console i think it should be supported via graph api as well. Thanks |
Sorry, let me clarify: the Intune PowerShell Sample scripts (found at https://github.com/microsoftgraph/powershell-intune-samples) is off topic for this repository. Please submit issues about the samples in that repo. Win32 LOB apps are an important feature in Intune. Currently, it is in the beta schema because it is a new feature. Once we are confident in the stability of this new API, we will promote it to v1.0. The PowerShell SDK is built on the v1.0 schema specifically for this reason - APIs in beta can change, and so building the SDK on the beta schema introduces the possibility of changes which can break the scripts that use it. Once the Win32 LOB app feature is available in the v1.0 schema, we will be able to provide it in the Intune PowerShell SDK as well. In terms of the console, our UI in the Azure Portal supports Win32 LOB apps because it makes calls to the beta schema. We do this because it allows us to iterate much faster to bring features to the UI. Regarding changes to the beta schema, we are able to prevent breaks in the UI as it is developed in parallel with our Graph APIs. |
Any script that we would build using the SDK would be far simpler than going with this method: Application_LOB_Add.ps1. I'd rather you break simple scripts using the API, than complex scripts such as those in the examples. Given how fast Intune is changing, it's not practical to wait for the SDK to only support v1.0 APIs. Win32 LoB apps were introduced in beta in October 2018, it's now April 2019. Please reconsider the stance for APIs that aren't v1.0 yet. At the very least, please support calling a beta API with |
So what now? Do we have to reverse-engineer the javascript on Azure Portal to get the special encoding/encryption? Please get someone to transcode it to PowerShell. I get as far as some others here... but the Azure Blob Upload seams to really need some different digested file for win32Apps. |
I simply want to replace the .intunewin file of an existing app programmatically with Graph API in PowerShell instead of doing it manually through the Intune portal, even if I need to use the beta API. This is very urgent. Is it possible? I have the .intunewin file ready to go, I just need to replace an existing Intune App's .intunewin file with this new one. |
hi tjgruber, you will have to use the msgraph api to query for an azure storage blob id, try it in the msgraph explorer. The Blob storage id will allow you to place the new intunewin container in azure, which has to be queried through the azure storage api. The example how to upload those files is in the win32 Lob powershell script. You will have to provide the id and the new file. If the id does not work, see what web-calls the azure portal ui issues and do the same with powershell invoke-webrequest. Can,t be more specific yet, but soon, when I will be facing a similar task, I will report back here, if still needed.(in around september i think) |
Hi Crucerio, I proceeded with your suggestion and was able to successfully upload and commit a new intunewin file to the win32lobapp. However, the app continues to use the old "committedContentVersion". When I go into the app in the Intune web GUI and manually upload a new intunewin file, the app automatically uses the package. But again, when I upload and commit the intunewin file through the API using some functions from Win32_Application_Add.ps1, the App does not use the newly uploaded intunewin file, it continues to use the old version. I confirm this when I look at the following URI and setting: https://graph.microsoft.com/beta/deviceAppManagement/mobileApps/$appID When I try to change the committedContentVersion manually in Graph Explorer to use the intunewin file I uploaded via API, It gives an error saying: So in summary, your suggestion worked and I was able to successfully upload and commit my intunewin file programmatically, but the problem now is that the app that I'm updating with this new file does not use the new file. It still deploys the old intunewin file, unless I upload a new one manually via the web GUI. So, how is the web gui telling the app to use the newly uploaded intunewin file? That's what I want to do now. |
Hi again tjgruber, the progress you already achieved sounds very close to the solution. The last bit will be found in the graph and storage api calls, when uploading a new container. Start logging the webrequests just before choosing a new file to upload in the azure portal. Meanwhile repeatedly query the app in msgraph to track down the time, when the actual app revision changes. That will give you the hint what payload has to be injected to the win32 app in msgraph. Maybe it just needs a reference to the completed upload, to be sure it‘s upload is complete. Hope this helps you track it down. If you succeed, some others here would sure be pleased to get that hint, too, me included. |
I couldn't figure it out. So I ended up altering that script to work in an Azure DevOps pipeline to make a new app and delete the old one for every update. There's some more testing to be done regarding how that will effect existing installations, but until there's an easier way to replace or update existing intunewin files programmatically or through graph api, that's what I have to do to move on. |
Yes you must have missed my earlier comments. I tried those and even though they successfully upload and commit the intunewin file, the InTune app does not use it, as it keeps using the previous version of the package. |
Why, is that possible to have more information on how to upload the files (.msi and .intunewin) via this module if supported?? we're trying to automate all creation and deployment via graph API but its hard to find documentation around it.
The text was updated successfully, but these errors were encountered: