Skip to content

Commit

Permalink
Adjust EvaluatorOptions to use project base URI(#21)
Browse files Browse the repository at this point in the history
* In `EvaluatorOptions`, replace `ProjectDir` with `ProjectBaseURI` (API breaking)
* `WithResourceReader` and `WithModuleReader` now append `:` to the scheme when appending to the allow-lists
* Correct typo in `DeclaredProjectDepenedencies` (API breaking)
* Add DEVELOPMENT.adoc with instructions on how to debug the `pkl server` subprocess
* Miscellaneous doc comment clarifications
  • Loading branch information
HT154 committed Jun 5, 2024
1 parent 56cbddc commit 1ccec69
Show file tree
Hide file tree
Showing 3 changed files with 66 additions and 17 deletions.
43 changes: 43 additions & 0 deletions DEVELOPMENT.adoc
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
:uri-pkl-repo: https://github.com/apple/pkl

= Pkl Go Development Guide

== Debugging the Pkl Server

The pkl-go evaluator API runs `pkl server` as a subprocess, which presents obstacles for directly debugging the server process.
It is possible to

*Debug Stub Setup*

. Create a file named `debugpkl`
. Mark the file executable with `chmod +x debugpkl`
. Populate the file with this content (note: the path to the executable will depend on where the Pkl repo is cloned):

[,shell]
----
#!/bin/sh
exec java -agentlib:jdwp=transport=dt_socket,server=n,address=localhost:5005,suspend=y -jar /path/to/pkl/pkl-cli/build/executable/jpkl "$@"
----


*IntelliJ IDEA Setup:*

. Open the {uri-pkl-repo}[pkl] project
. Build `jpkl` by running `./gradlew javaExecutable` so it is available to the script defined above
. Run > Edit Configurations...
. Add a new "Remote JVM Debug" configuration
. Provide a name, eg. `debugpkl`
. Under "Configuration", select the "Listen to remote JVM" debugger mode
. Enable "Auto restart"
. Ensure Host is "localhost" and Port is "5005"

*Usage*

. Configure pkl-go to use `debugpkl` as the server executable: `export PKL_EXEC=./debugpkl`
. Optionally, turn on extra debug output: `export PKL_DEBUG=1`
. Define breakpoints as desired in the Pkl codebase using IntelliJ
. In IntelliJ, start debugging the "Remote JVM Debug" configuration defined above
. Execute the process using pkl-go

When the Pkl server execution reaches a defined breakpoint, it will pause and activate the debugger in IntelliJ.
39 changes: 22 additions & 17 deletions pkl/evaluator_options.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@
package pkl

import (
"fmt"
"io/fs"
"os"
"path/filepath"
Expand Down Expand Up @@ -57,10 +56,16 @@ type EvaluatorOptions struct {
// - `"yaml"`
OutputFormat string

// AllowedModules is the URI patterns that determine which modules can be loaded and evaluated.
// AllowedModules defines URI patterns that determine which modules are permitted to be loaded and evaluated.
// Patterns are regular expressions in the dialect understood by [java.util.regex.Pattern].
//
// [java.util.regex.Pattern]: https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/util/regex/Pattern.html
AllowedModules []string

// AllowedResources is the URI patterns that determine which resources can be loaded and evaluated.
// AllowedResources defines URI patterns that determine which resources are permitted to be loaded and evaluated.
// Patterns are regular expressions in the dialect understood by [java.util.regex.Pattern].
//
// [java.util.regex.Pattern]: https://docs.oracle.com/en/java/javase/17/docs/api/java.base/java/util/regex/Pattern.html
AllowedResources []string

// ResourceReaders are the resource readers to be used by the evaluator.
Expand All @@ -79,11 +84,11 @@ type EvaluatorOptions struct {
// Attempting to read past the root directory is an error.
RootDir string

// ProjectDir is the project directory for the evaluator.
// ProjectBaseURI sets the project base path for the evaluator.
//
// Setting this determines how Pkl resolves dependency notation imports.
// It causes Pkl to look for the resolved dependencies relative to this directory,
// and load resolved dependencies from a PklProject.deps.json file inside this directory.
// It causes Pkl to look for the resolved dependencies relative to this base URI,
// and load resolved dependencies from `PklProject.deps.json` within the base path represented.
//
// NOTE:
// Setting this option is not equivalent to setting the `--project-dir` flag from the CLI.
Expand All @@ -98,13 +103,13 @@ type EvaluatorOptions struct {
//
// To emulate the CLI's `--project-dir` flag, create an evaluator with NewProjectEvaluator,
// or EvaluatorManager.NewProjectEvaluator.
ProjectDir string
ProjectBaseURI string

// DeclaredProjectDepenedencies is set of dependencies available to modules within ProjectDir.
// DeclaredProjectDepenedencies is set of dependencies available to modules within ProjectBaseURI.
//
// When importing dependencies, a PklProject.deps.json file must exist within ProjectDir
// When importing dependencies, a PklProject.deps.json file must exist within ProjectBaseURI
// that contains the project's resolved dependencies.
DeclaredProjectDepenedencies *ProjectDependencies
DeclaredProjectDependencies *ProjectDependencies
}

type ProjectRemoteDependency struct {
Expand Down Expand Up @@ -202,12 +207,12 @@ func (e *EvaluatorOptions) toMessage() *msgapi.CreateEvaluator {
}

func (e *EvaluatorOptions) project() *msgapi.ProjectOrDependency {
if e.ProjectDir == "" {
if e.ProjectBaseURI == "" {
return nil
}
return &msgapi.ProjectOrDependency{
ProjectFileUri: fmt.Sprintf("file://%s/PklProject", e.ProjectDir),
Dependencies: e.DeclaredProjectDepenedencies.toMessage(),
ProjectFileUri: e.ProjectBaseURI + "/PklProject",
Dependencies: e.DeclaredProjectDependencies.toMessage(),
}
}

Expand Down Expand Up @@ -258,7 +263,7 @@ var WithDefaultCacheDir = func(opts *EvaluatorOptions) {
var WithResourceReader = func(reader ResourceReader) func(opts *EvaluatorOptions) {
return func(opts *EvaluatorOptions) {
opts.ResourceReaders = append(opts.ResourceReaders, reader)
opts.AllowedResources = append(opts.AllowedResources, reader.Scheme())
opts.AllowedResources = append(opts.AllowedResources, reader.Scheme()+":")
}
}

Expand All @@ -267,7 +272,7 @@ var WithResourceReader = func(reader ResourceReader) func(opts *EvaluatorOptions
var WithModuleReader = func(reader ModuleReader) func(opts *EvaluatorOptions) {
return func(opts *EvaluatorOptions) {
opts.ModuleReaders = append(opts.ModuleReaders, reader)
opts.AllowedModules = append(opts.AllowedModules, reader.Scheme())
opts.AllowedModules = append(opts.AllowedModules, reader.Scheme()+":")
}
}

Expand Down Expand Up @@ -321,8 +326,8 @@ var WithProjectEvaluatorSettings = func(project *Project) func(opts *EvaluatorOp
// WithProjectDependencies configures the evaluator with dependencies from the specified project.
var WithProjectDependencies = func(project *Project) func(opts *EvaluatorOptions) {
return func(opts *EvaluatorOptions) {
opts.ProjectDir = strings.TrimPrefix(strings.TrimSuffix(project.ProjectFileUri, "/PklProject"), "file://")
opts.DeclaredProjectDepenedencies = project.Dependencies()
opts.ProjectBaseURI = strings.TrimSuffix(project.ProjectFileUri, "/PklProject")
opts.DeclaredProjectDependencies = project.Dependencies()
}
}

Expand Down
1 change: 1 addition & 0 deletions pkl/reader.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import (
// Reader is the base implementation shared by a ResourceReader and a ModuleReader.
type Reader interface {
// Scheme returns the scheme part of the URL that this reader can read.
// The value should be the URI scheme up to (not including) ":"
Scheme() string

// IsGlobbable tells if this reader supports globbing via Pkl's `import*` and `glob*` keywords
Expand Down

0 comments on commit 1ccec69

Please sign in to comment.