Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 42 additions & 16 deletions sdkbuild/ruby.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,20 @@ type BuildRubyProgramOptions struct {
// If present, this directory is expected to exist beneath base dir. Otherwise
// a temporary dir is created.
DirName string
// If present, additional gems to add to the generated Gemfile.
MoreDependencies []RubyDependency
// If present, custom writers that will capture stdout/stderr.
Stdout io.Writer
Stderr io.Writer
}

// RubyDependency is an additional gem dependency for the generated Gemfile.
type RubyDependency struct {
Name string
Version string
Path string
}

// RubyProgram is a Ruby-specific implementation of Program.
type RubyProgram struct {
dir string
Expand Down Expand Up @@ -79,7 +88,7 @@ func BuildRubyProgram(ctx context.Context, options BuildRubyProgramOptions) (*Ru
// Build the Gemfile content. We use Bundler's `gemspec` directive to
// auto-discover the gemspec in the source directory (via path: option).
// This works for any gem name (harness, omes, etc.).
var gemfileContent string
gemfileLines := []string{`source "https://rubygems.org"`, ""}
if strings.ContainsAny(options.Version, `/\`) {
// It's a path to a local SDK repo
sdkPath, err := filepath.Abs(options.Version)
Expand All @@ -95,25 +104,22 @@ func BuildRubyProgram(ctx context.Context, options BuildRubyProgramOptions) (*Ru
return nil, fmt.Errorf("failed finding temporalio.gemspec in version dir: %w", err)
}
}
gemfileContent = fmt.Sprintf(`source "https://rubygems.org"

gem "temporalio", path: %q
gemspec path: %q
`, gemPath, sourceDir)
gemfileLines = append(gemfileLines, fmt.Sprintf(`gem "temporalio", path: %q`, gemPath))
} else if options.Version != "" {
version := strings.TrimPrefix(options.Version, "v")
gemfileContent = fmt.Sprintf(`source "https://rubygems.org"

gem "temporalio", "%s"
gemspec path: %q
`, version, sourceDir)
} else {
// No version constraint — Bundler resolves to latest from RubyGems
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Was dropping support for temporalio without a version constraint intetional?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, so we're not dropping support for this, it's just that the code to do this is no longer in the conditional:

	gemfileLines := []string{`source "https://rubygems.org"`, ""}
	... branch conditionals where `version` is specified...
	gemfileLines = append(gemfileLines, fmt.Sprintf(`gemspec path: %q`, sourceDir), "")

because we did the same thing regardless of which conditional branch we went down

gemfileContent = fmt.Sprintf(`source "https://rubygems.org"
gemfileLines = append(gemfileLines, fmt.Sprintf(`gem "temporalio", %q`, version))
}

gemspec path: %q
`, sourceDir)
moreDependencyLines, err := renderRubyDependencies(options.MoreDependencies)
if err != nil {
return nil, err
}
if len(moreDependencyLines) > 0 {
gemfileLines = append(gemfileLines, moreDependencyLines...)
gemfileLines = append(gemfileLines, "")
}
gemfileLines = append(gemfileLines, fmt.Sprintf(`gemspec path: %q`, sourceDir), "")
gemfileContent := strings.Join(gemfileLines, "\n")

if err := os.WriteFile(filepath.Join(dir, "Gemfile"), []byte(gemfileContent), 0644); err != nil {
return nil, fmt.Errorf("failed writing Gemfile: %w", err)
Expand Down Expand Up @@ -157,6 +163,26 @@ gemspec path: %q
return &RubyProgram{dir: dir, source: sourceDir}, nil
}

func renderRubyDependencies(dependencies []RubyDependency) ([]string, error) {
lines := make([]string, 0, len(dependencies))
for _, dependency := range dependencies {
if dependency.Name == "" {
return nil, fmt.Errorf("ruby dependency name required")
}
if dependency.Path != "" && dependency.Version != "" {
return nil, fmt.Errorf("ruby dependency %q cannot have both path and version", dependency.Name)
}
if dependency.Path != "" {
lines = append(lines, fmt.Sprintf(`gem %q, path: %q`, dependency.Name, dependency.Path))
} else if dependency.Version != "" {
lines = append(lines, fmt.Sprintf(`gem %q, %q`, dependency.Name, dependency.Version))
} else {
lines = append(lines, fmt.Sprintf(`gem %q`, dependency.Name))
}
}
return lines, nil
}

// RubyProgramFromDir recreates the Ruby program from a Dir() result of a
// BuildRubyProgram(). The sourceDir should point to the directory containing
// the gemspec and runner.rb.
Expand Down
Loading