Skip to content

[SR-11432] Declarative package description for SwiftPM using Function Builders #4665

@swift-ci

Description

@swift-ci
Previous ID SR-11432
Radar None
Original Reporter kitasuke (JIRA User)
Type New Feature
Status Closed
Resolution Won't Do
Additional Detail from JIRA
Votes 0
Component/s Package Manager
Labels New Feature
Assignee kitasuke (JIRA)
Priority Medium

md5: 063f185e77f07f6591ed8271b385975c

Issue Description:

Overview

I would like to make a propose to have declarative package description by using function builder as alternative way. I think we can keep current way as it is.

There are pros and cons. This case might not work with function builders because package description has type constraints in the tree structure, but I would love to hear your opinions.

Pros

  • Declarative description

  • More understandable API

Cons

  • Can't have type constraints for all of contents unless we defined function builder for specific types

  • Compiler error is not friendly when we have wrong content at unexpected place

let package = Package(name: "Paper") {
    ProductList {
        Product(name: "tool", type: .static) {
            TargetList {
                Target(name: "tool")
            }
        }
    }
    DependencyList {
        Dependency(
            url: "http://example.com.com/ExamplePackage/ExamplePackage",
            from: "1.2.3"
        )
        Dependency(url: "dev", exact: "1.2.3")
    }
    TargetList {
        Target(name: "tool") {
            TargetDependencyList {
                TargetDependency(name: "Paper")
                TargetDependency(name: "ExamplePackage")
            }
        }
        Target(name: "Paper") {
            TargetDependencyList {
                TargetDependency(name: "Basic")
                Target(name: "Utility")
                Product(name: "AnotherExamplePackage")
            }
        }
    }
}

Here is my rough implementation of the functionality. Encoded data would be interface for current implementation of package description.

https://gist.github.com/kitasuke/ee73934c2eda0f63bbd371b69380c443

With this implementation, description above can be encoded because it conforms to Encodable, so that this can be mapped to existing structure easily. Here is sample encoded output as JSON

{
  "targets": [
    {
      "name": "tool",
      "dependencies": [
        {
          "name": "Paper"
        },
        {
          "name": "ExamplePackage"
        }
      ]
    },
    {
      "name": "Paper",
      "dependencies": [
        {
          "name": "Basic"
        },
        {
          "name": "Utility"
        },
        {
          "name": "AnotherExamplePackage",
          "type": "executable"
        }
      ]
    }
  ],
  "name": "Paper",
  "dependencies": [
    {
      "url": "http://example.com.com/ExamplePackage/ExamplePackage",
      "from": "1.2.3"
    },
    {
      "url": "dev",
      "exact": "1.2.3"
    }
  ],
  "products": [
    {
      "name": "tool",
      "type": "static",
      "targets": [
        {
          "name": "tool"
        }
      ]
    }
  ]
}

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions