is env variable referencing supported?

tslade
tslade
Community Member
edited October 2023 in CLI

Hi,

Hoping someone can help answer my question...

In my NodeJS project, I use the 1Password cli to load my secrets into my env file using the 'op run' command. e.g.
op run --env-file="./.env.local" -- npm start

In my .env.local file, i'm attempting to reference an environment variable where the value is being fetched from my 1Password vault. Example env file below:

VITE_SITE_LINK="op://example/dev/site-url"
VITE_SITE_PRIVACY_LINK=${VITE_SITE_LINK}/privacy-policy

However, I'm getting the following error:
[ERROR] 2023/10/17 15:11:22 item example/5pviavnxgs7lqeimhzeu73blje does not have a field VITE_SITE_LINK.privacy-policy


1Password Version: 8.10.16
Extension Version: Not Provided
OS Version: macOS 13.5.2
Browser: Not Provided
1Password CLI Version: 2.21.0

Comments

  • philmcole
    philmcole
    Community Member
    edited December 2023

    Same here. I'd like to define the secret reference as part of some string in the .env file.

    .env file

    GITHUB_TOKEN="op://foo/bar/token"
    DENO_AUTH_TOKENS="${GITHUB_TOKEN}@raw.githubusercontent.com"
    

    error

    [ERROR] 2023/12/22 12:57:07 invalid secret reference 'op://foo/bar/token@raw.githubusercontent.com': invalid character in secret reference: '@'
    
  • scottohara
    scottohara
    Community Member

    I've stumbled on this thread because I'm having the same issue, and after trying numerous different approaches, I'm left wondering why this doesn't work.

    Let's start with a simple example that uses enclosed secret references:

    .env

    DATABASE_URL="http://{{op://private/my_app/username}}:{{op://private/my_app/password}}@localhost:1234"
    

    Checking this with op inject returns the expected result, with the two secret refs replaced with the values "bob" and "secret" respectively; but running through op run and printenv doesn't:

    $ op inject -i .env
    DATABASE_URL="http://bob:secret@localhost:1234"
    
    $ op run --env-file=.env --no-masking -- printenv DATABASE_URL
    http://{{op://private/my_app/username}}:{{op://private/my_app/password}}@localhost:1234
    

    So it seems that constructing an ENV value by embedding enclosed secret refs into a string doesn't work.

    Let's try a different approach using multiple ENV vars:

    .env

    USERNAME="op://private/my_app/username"
    PASSWORD="op://private/my_app/password"
    DATABASE_URL="http://${USERNAME}:${PASSWORD}@localhost:1234"
    
    $ op inject -i .env                              
    USERNAME=bob
    PASSWORD=secret
    DATABASE_URL="http://${USERNAME}:${PASSWORD}@localhost:1234"
    
    $op run --env-file=.env --no-masking -- printenv USERNAME
    bob
    
    $op run --env-file=.env --no-masking -- printenv PASSWORD
    secret
    
    $ op run --env-file=.env --no-masking -- printenv DATABASE_URL
    http://op://private/my_app/username:op://private/my_app/password@localhost:1234
    

    Again, we can see that op inject seems to have correctly substituted the USERNAME and PASSWORD values, and left DATABASE_URL unchanged (with the assumption that they would be correctly expanded when a process tries to read $DATABASE_URL).

    We can also see that op run has correctly resolved the USERNAME and PASSWORD vars, but now DATABASE_URL has been substituted with....the secret refs?

    (I've tried this this with/without quotes, with/without curly braces etc. Nothing seems to work).

    One more, just to really confuse things:

    .env

    USERNAME="op://private/my_app/username"
    PASSWORD="op://private/my_app/password"
    DATABASE_USERNAME="${USERNAME}"
    DATABASE_PASSWORD="${PASSWORD}"
    
    $ op inject -i .env
    USERNAME="bob"
    PASSWORD="secret"
    DATABASE_USERNAME="${USERNAME}"
    DATABASE_PASSWORD="${PASSWORD}"
    
    $ op run --env-file=.env --no-masking -- printenv DATABASE_USERNAME  
    bob
    
    $ op run --env-file=.env --no-masking -- printenv DATABASE_PASSWORD
    secret
    

    Wait, what? That works?

    Here we have two ENV vars ($DATABASE_USERNAME and $DATABASE_PASSWORD) that reference to other ENV vars ($USERNAME and $PASSWORD) that are using secret refs....and it all works fine?

    The difference here seems to be referencing a $VAR on its own ("${USERNAME}") is fine, but referencing it inside a string ("xx${USERNAME}") is not?

    It seems like this should all just work.

  • snowy
    snowy
    Community Member
    edited June 24
    $ op run --env-file=.env --no-masking -- printenv DATABASE_URL | op inject
    
    

    if the completion is pushed to op inject the references will be completed. I am not sure env variables are intended to be used that way. Cause i believe they are read "as is".