Skip to content
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

Support NuGet packages for external dependencies #261

Open
freddydk opened this issue Oct 24, 2022 · 2 comments
Open

Support NuGet packages for external dependencies #261

freddydk opened this issue Oct 24, 2022 · 2 comments
Assignees
Labels
enhancement New feature or request In Preview Currently available in AL-Go for GitHub preview In Progress Issue is actively being worked on

Comments

@freddydk
Copy link
Contributor

freddydk commented Oct 24, 2022

Note

Changes to the implementation made on December 18th 2023

Summary

Why NuGet?

Creating a Business Central specific package format, a package manager, integrating this in GitHub Packages and Azure Artifacts and potentially building a public feed for BC packages seems like overkill. Cheapest and best approach would be to find a suitable package format.

Azure Artifacts supports NuGet, Maven, npm, Gradle and Universal Packages.
GitHub packages supports NuGet, Maven, npm, pip and RubyGems
Nuget.org obviously supports NuGet

Even though Universal packages (from a technology standpoint) seems like the right choice, we should not settle on a format, which isn't natively supported by GitHub packages. Maven is mostly used for Java and doesn't seem like the right format.

npm is for node.js modules and NuGet is for dotnet packages, both formats could be used, but NuGet seems to be the easiest to work with wrt simplicity (just a .zip file) and access (public API for NuGet feed servers)

NuGet package format

The NuGet package format is described here: https://learn.microsoft.com/en-us/nuget/reference/nuspec

BcNuGet package format

A BcNuGet package contains exactly one .app file (or a runtime package)

A normal BcNuGet package is formattet like:

manifest.nuspec
filename.app

Sample manifest.nuspec:

<?xml version="1.0" encoding="utf-8"?>
<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
    <metadata>
        <id>FreddyKristiansen.BingMapsPTE.165d73c1-39a4-4fb6-85a5-925edc1684fb</id>
        <version>4.4.3.0</version>
        <title>BingMaps.PTE</title>
        <description>BingMaps Integration App with geocode functionality and map control</description>
        <authors>Freddy Kristiansen</authors>
        <repository type="git" url="https://github.com/microsoft/bcsamples-bingmaps.pte" />
        <dependencies>
            <dependency id="Microsoft.Application" version="20.1.39764.40432" />
            <dependency id="Microsoft.Platform" version="20.0.39668.40349" />
        </dependencies>
    </metadata>
    <files>
        <file src="Freddy%20Kristiansen_BingMaps.PTE_4.4.3.0.app" target="Freddy%20Kristiansen_BingMaps.PTE_4.4.3.0.app" />
    </files>
</package>

Must contain id, version, title, description and authors.
For GitHub, repository should point to the owning repository of the package.

The default naming of nuget packages is Publisher.Name.AppId (where publisher and name are normalized - i.e. spaces, dots and special characters are removed, dashes are kept.)

Dependencies includes all dependencies (including Application dependency and Platform dependency)

Dependency resolution is done on the AppId only (if the package/dependency name ends with a GUID - considered to be the appid) - if the name does not end with an AppId, then the full name is used for dependency resolution)

Referencing a BcNuGet Package in your project

In app.json you include a reference to the app on which you have a dependency, like:

{
    "id":  "165d73c1-39a4-4fb6-85a5-925edc1684fb",
    "name":  "BingMaps.PTE",
    "publisher":  "Freddy Kristiansen",
    "version":  "1.0.0.0"
},

In your AL-Go repository settings you specify a list of trusted NuGet feeds like:

"TrustedNuGetFeeds": [
    {
        "Url": "https://api.nuget.org/v3/index.json",
        "Patterns": [ "Microsoft.*" ]
    },
    {
        "Url": "https://api.nuget.org/v3/index.json",
        "Fingerprints": [ "DFE254D1477DF4133CB9C69EEF6AE0E5DC334C85A2901D6ADA3D18495D74B260" ]
    },
    {
        "Url": "https://nuget.pkg.github.com/businesscentralapps/index.json",
        "AuthTokenSecret": "GhTokenWorkflow"
    },
    {
        "Url": "https://pkgs.dev.azure.com/freddydk/apps/_packaging/MyApps/nuget/v3/index.json"
    }
]

Patterns specifies which package patterns are considered in the corresponding feed. This can be the full name of a package, a registered prefix (like microsoft.*), but please note that anybody can publish malicious packages to f.ex. nuget.org, so please only trust registered prefixes or only signed packages.

Fingerprints specifies that you only want to consider packages, which are signed with any of the fingerprints in the array. Note that NuGet.org signs all packages with a repository signature. That one should not be trusted - you should trust only author signatures.

If no AuthTokenSecret specified, the nuget feed is considered public.

If a downloaded package contains dependencies to other NuGet packages, these are downloaded from the same nuget feed or other trusted nuget feeds.

NOTE that All trusted feeds are searched for a dependency to be resolved. If

Versioning

NuGet package versioning will have the same version as the app contained.
NuGet package versioning and dependency versioning follows this schema:
https://learn.microsoft.com/en-us/nuget/concepts/package-versioning

BcContainerHelper does support pre-release packages - this support will be added to AL-Go for GitHub as well.

A Public feed for Microsoft apps

Microsoft is planning on creating a public NuGet feed for all Microsoft apps. This NuGet feed will automatically be trusted by BcContainerHelper. A Proof-Of-Concept implementation of this feed can be found here: https://pkgs.dev.azure.com/freddydk/apps/_packaging/MyApps/nuget/v3/index.json

A Public feed for AppSource app symbols

Microsoft is also planning on creating a public NuGet feed containing NuGet packages for symbols for AppSource apps., This NuGet feed will automatically be trusted by BcContainerHelper.

Generation of NuGet packages

AL-Go for GitHub will have support for generating, delivering and updating NuGet packages with the content of a repository.
Main part of the functionality will reside in BcContainerHelper and can be used in other DevOps solutions as well.

Downloading NuGet packages

BcContainerHelper will have functionality for downloading BcNuGet packages, which will be used by AL-Go. This function will among other things have a parameter specifying which apps are already installed / existing. Apps in this collection will NOT be downloaded.

Try it out

Run Update AL-Go System Files with freddydk/AL-Go@nuget to try out the latest version of this.

@freddydk freddydk self-assigned this Oct 24, 2022
@freddydk freddydk added the Under Investigation Issue is under investigation label Oct 24, 2022
@freddydk freddydk changed the title Support NuGet packages for dependencies Support NuGet packages for external dependencies Oct 24, 2022
@microsoft microsoft deleted a comment from FreundDK Oct 24, 2022
@danielgorski-bynd365
Copy link

Yeah, looking forward! 🚀🚀🚀

@freddydk freddydk added In Preview Currently available in AL-Go for GitHub preview In Progress Issue is actively being worked on enhancement New feature or request and removed Under Investigation Issue is under investigation labels Nov 12, 2023
@ronnykwon
Copy link

Can't wait to try this as it will unlock a big constraint in our CI/CD

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request In Preview Currently available in AL-Go for GitHub preview In Progress Issue is actively being worked on
Projects
Status: 👀 In preview
Development

No branches or pull requests

4 participants
@ronnykwon @freddydk @danielgorski-bynd365 and others