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

Allow to override environment on spring client startup #654

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
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
27 changes: 27 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -358,6 +358,16 @@ end
If you want to register multiple callbacks you can simply call
`Spring.after_fork` multiple times with different blocks.

If you accept an argument, it will contain an object with information about the
Spring client request and server state. You can use it to detect environment
variable mismatch between the invocation and the spring instance startup:

```ruby
Spring.after_fork do |cb|
raise "error" if cb.env['MASTER'].present? && cb.env['MASTER'] != ENV['MASTER']
end
```

### Watching files and directories

Spring will automatically detect file changes to any file loaded when the server
Expand Down Expand Up @@ -386,6 +396,23 @@ a command runs:
Spring.quiet = true
```

### Environment variable overrides

When the spring server starts up a new instance of the application, it does not
set all environment variables by default. Only the environment variables that
were set when the spring server started and were not changed by the application
are propagated.

This can be customized with `Spring.env_override`:

- `Spring.env_override = false` : default behavior noted above

- `Spring.env_override = true` : all variables are applied, regardless of if
they were changed by the application or not.

- `Spring.env_override = []` (array of strings) : in addition to the usual
behavior, the variable listed here will be propagated

### Environment variables

The following environment variables are used by Spring:
Expand Down
26 changes: 22 additions & 4 deletions lib/spring/application.rb
Original file line number Diff line number Diff line change
Expand Up @@ -187,13 +187,27 @@ def serve(client)
# Delete all env vars which are unchanged from before Spring started
original_env.each { |k, v| ENV.delete k if ENV[k] == v }

# if env_override is an array, delete the variables listed
if Spring.env_override.is_a? Array
Spring.env_override.each { |k| ENV.delete k }
end

# Load in the current env vars, except those which *were* changed when Spring started
env.each { |k, v| ENV[k] ||= v }
# if env_override is true, load in *all* the current vars
env.each do |k, v|
if Spring.env_override == true
ENV[k] = v
else
ENV[k] ||= v
end
end

connect_database
srand

invoke_after_fork_callbacks
invoke_after_fork_callbacks(OpenStruct.new(
Copy link
Member

Choose a reason for hiding this comment

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

Can we create a class for this object here? It would allow us to document it for example.

env: env,
original_env: original_env))
shush_backtraces

command.call
Expand Down Expand Up @@ -256,9 +270,13 @@ def setup(command)
end
end

def invoke_after_fork_callbacks
def invoke_after_fork_callbacks(arg)
Spring.after_fork_callbacks.each do |callback|
callback.call
if callback.arity == 1
callback.call(arg)
else
callback.call
end
end
end

Expand Down
3 changes: 2 additions & 1 deletion lib/spring/configuration.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

module Spring
class << self
attr_accessor :application_root, :quiet
attr_accessor :application_root, :quiet, :env_override

def gemfile
if /\s1.9.[0-9]/ === Bundler.ruby_scope.gsub(/[\/\s]+/,'')
Expand Down Expand Up @@ -55,4 +55,5 @@ def find_project_root(current_dir)
end

self.quiet = false
self.env_override = false
end