Nutmeg Plundering Muse

    ts-yaml
    TypeScript icon, indicating that this package has built-in type declarations

    1.0.0 • Public • Published

    ts-yaml

    YAML is awesome!

    • Easy to learn.
    • Minimal syntax.

    But it has some drawbacks, especially as YAML files scale.

    • No types/code completion.
    • Ambiguous syntax.
    • No control flow (e.g. ternary operator, functions, map).

    This is an experiment to define types for YAML in TypeScript, with the goal of easily generating typechecked YAML.

    Examples

    Buildkite pipleines

    Here's a sample pipelines.yml file for Buildkite CI:

    steps:
      command: "FIXTURE=cplusplus,schema-cplusplus,kotlin,graphql .buildkite/build-pr.sh"
        label: "C++ Kotlin GraphQL"
     
      command: "FIXTURE=java,schema-java,schema-json-csharp .buildkite/build-pr.sh"
        label: "java schema-json-c#"
     
      command: "FIXTURE=typescript,schema-typescript,javascript,schema-javascript,flow,schema-flow,json-ts-csharp .buildkite/build-pr.sh"
        label: "typescript javascript flow"
     
      command: "FIXTURE=swift,schema-swift,rust,schema-rust,elm,schema-elm .buildkite/build-pr.sh"
        label: "swift rust elm"
     
      command: "FIXTURE=csharp,schema-csharp,ruby,schema-ruby,golang,schema-golang .buildkite/build-pr.sh"
        label: "csharp ruby golang"

    Let's write the type of the YAML in TypeScript. Immediately we have a lot more information than is evident in the YAML sample:

    interface Step {
      command: string | string[];
      label?: string;
      branches?: string;
      env?: { [name: string]: string };
      agents?: { [key: string]: string };
      artifact_paths?: string;
      parallelism?: number;
      concurrency?: number;
      concurrency_group?: string;
      timeout_in_minutes?: number;
      skip?: boolean | string;
      retry?:
        | { automaticboolean | AutomaticRetryConditions }
        | { manualboolean | ManualRetryConditions };
    }
     
    interface AutomaticRetryConditions {
      exit_status?: "*" | number;
      limit?: 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10;
    }
     
    interface ManualRetryConditions {
      allowed?: boolean;
      reason?: string;
      permit_on_pass?: boolean;
    }
     
    declare var steps: Step[];

    Let's make a file named pipeline.yml.ts and define the steps global variable, and we immediately get code completion where we would otherwise have to search Buildkite's docs:

    We can finish defining our CI steps:

    import "yaml/buildkite";
     
    const fixtures = [
      "cplusplus,schema-cplusplus,kotlin,graphql",
      "java,schema-java,schema-json-csharp",
      "typescript,schema-typescript,javascript,schema-javascript,flow,schema-flow,json-ts-csharp",
      "swift,schema-swift,rust,schema-rust,elm,schema-elm",
      "csharp,schema-csharp,ruby,schema-ruby,golang,schema-golang"
    ];
     
    steps = fixtures.map(fixture => ({
      command: `FIXTURE=${fixture} .buildkite/build-pr.sh`,
      label: fixture
    }));

    Using:

    • steps is typechecked
    • String interpolation
    • Data (list of fixtures)
    • map

    Output YAML with ts-yaml pipeline.yaml.ts.

    Keywords

    none

    Install

    npm i ts-yaml

    DownloadsWeekly Downloads

    722

    Version

    1.0.0

    License

    ISC

    Unpacked Size

    3.83 kB

    Total Files

    4

    Last publish

    Collaborators

    • dvdsgl