Skip to content

std: Refactor env::_var function#151690

Open
xtqqczze wants to merge 1 commit intorust-lang:mainfrom
xtqqczze:env-var
Open

std: Refactor env::_var function#151690
xtqqczze wants to merge 1 commit intorust-lang:mainfrom
xtqqczze:env-var

Conversation

@xtqqczze
Copy link
Contributor

No description provided.

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-libs Relevant to the library team, which will review and decide on the PR/issue. labels Jan 26, 2026
@rustbot
Copy link
Collaborator

rustbot commented Jan 26, 2026

r? @jhpratt

rustbot has assigned @jhpratt.
They will have a look at your PR within the next two weeks and either review your PR or reassign to another reviewer.

Use r? to explicitly pick a reviewer

@rustbot
Copy link
Collaborator

rustbot commented Jan 26, 2026

This PR was rebased onto a different main commit. Here's a range-diff highlighting what actually changed.

Rebasing is a normal part of keeping PRs up to date, so no action is needed—this note is just to help reviewers.

@rust-log-analyzer

This comment has been minimized.

@xtqqczze xtqqczze changed the title std: Refactor _var function to use env_imp::getenv std: Refactor env::_var function Jan 26, 2026
@rust-log-analyzer
Copy link
Collaborator

The job x86_64-gnu-tools failed! Check out the build log: (web) (plain enhanced) (plain)

Click to see the possible cause of the failure (guessed by this bot)
REPOSITORY                                   TAG       IMAGE ID       CREATED      SIZE
ghcr.io/dependabot/dependabot-updater-core   latest    354d02aa29ac   7 days ago   783MB
=> Removing docker images...
Deleted Images:
untagged: ghcr.io/dependabot/dependabot-updater-core:latest
untagged: ghcr.io/dependabot/dependabot-updater-core@sha256:596da3f22bcbdff2c96fd7126001278022c834c1621c5efa2ad1a7794590636c
deleted: sha256:354d02aa29acf525570c732b6e006ecf138de6d63ca525d552eb4b24880ddc6c
deleted: sha256:8b7af0e426bc2cbeeacfd96b8354d3b80016991520977197e62090e47abaede8
deleted: sha256:cadf11ef1de7fdd5eab563757942353684047f09b212dc99d6ed48e8acf34d62
deleted: sha256:569b0caf9d5285db44ccd2629a3470139eea755be423a33a54d8a24cb3926bfa
deleted: sha256:f9dc5feb048d8f9fd43137e3998f59e9acfbd76c47a4e14984d109654119e282
---
tests/ui/drain_collect.fixed ... ok
tests/ui/double_parens.rs ... ok
tests/ui/duplicate_underscore_argument.rs ... ok
tests/ui/duplicated_attributes.rs ... ok
tests/ui/duration_suboptimal_units.rs ... ok
tests/ui/duration_suboptimal_units_days_weeks.rs ... ok
tests/ui/duration_subsec.rs ... ok
tests/ui/duration_suboptimal_units_days_weeks.fixed ... ok
tests/ui/double_parens.fixed ... ok
tests/ui/duration_suboptimal_units.fixed ... ok
tests/ui/duration_subsec.fixed ... ok
tests/ui/else_if_without_else.rs ... ok
tests/ui/elidable_lifetime_names.rs ... ok
---
[WARNING] line 39: Delta is 0 for "x", maybe try to use `compare-elements-position` instead?

======== tests/rustdoc-gui/setting-go-to-only-result.goml ========

[ERROR] setting-go-to-only-result output:
Execution context was destroyed, most likely because of a navigation.
stack: Error: Execution context was destroyed, most likely because of a navigation.
    at rewriteError (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/cdp/ExecutionContext.js:457:15)
    at async #evaluate (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/cdp/ExecutionContext.js:389:60)
    at async ExecutionContext.evaluate (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/cdp/ExecutionContext.js:277:16)
    at async IsolatedWorld.evaluate (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/cdp/IsolatedWorld.js:100:16)
    at async CdpFrame.evaluate (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/api/Frame.js:362:20)
    at async CdpPage.evaluate (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/puppeteer-core/lib/cjs/puppeteer/api/Page.js:826:20)
    at async /checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/browser-ui-test/src/index.js:432:28
    at async waitForConditionTrue (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/browser-ui-test/src/utils.js:209:13)
    at async runAllCommands (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/browser-ui-test/src/index.js:431:22)
    at async innerRunTestCode (/checkout/obj/build/x86_64-unknown-linux-gnu/test/rustdoc-gui/node_modules/browser-ui-test/src/index.js:714:21)



<= doc-ui tests done: 146 succeeded, 1 failed, 0 filtered out

Some(s) => s.into_string().map_err(VarError::NotUnicode),
None => Err(VarError::NotPresent),
}
env_imp::getenv(key).ok_or(VarError::NotPresent)?.into_string().map_err(VarError::NotUnicode)
Copy link
Contributor

Choose a reason for hiding this comment

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

I'm unsure why this refactoring is necessary. It looks like var_os(key) wraps around env_imp::getenv(key) and does what you're doing (or what you want to do) with match cases:

/// Doc comments omitted
#[stable(feature = "env", since = "1.0.0")]
pub fn var<K: AsRef<OsStr>>(key: K) -> Result<String, VarError> {
    _var(key.as_ref())
}

fn _var(key: &OsStr) -> Result<String, VarError> {
    match var_os(key) {
        Some(s) => s.into_string().map_err(VarError::NotUnicode),
        None => Err(VarError::NotPresent),
    }
}

/// Doc comments omitted
#[must_use]
#[stable(feature = "env", since = "1.0.0")]
pub fn var_os<K: AsRef<OsStr>>(key: K) -> Option<OsString> {
    _var_os(key.as_ref())
}

fn _var_os(key: &OsStr) -> Option<OsString> {
    env_imp::getenv(key)
}

Although, I'll admit, I'm curious on about the separate _var_os() and _var() functions here; I'm not noticing anywhere else _var_os() and _var() is used, so it makes me wonder why not just put what's inside _var_os()/_var() inside var_os()/var()?

Copy link
Member

Choose a reason for hiding this comment

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

The split exists to minimize the size of the generic versions.

Copy link
Contributor

Choose a reason for hiding this comment

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

Oh got it, that makes sense to me!

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I'm unsure why this refactoring is necessary.

Primarily to avoid: var -> _var -> -> var_os -> _var_os -> env_imp::getenv

When we can do: var -> _var -> env_imp::getenv

Replacing match with combinators because I thought it read a bit nicer

Copy link
Contributor

Choose a reason for hiding this comment

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

Yea I can definitely see the layers of function indirection here; I'm wondering if the compiler would optimize this away though and inline it?

Still, I'm with @hkBst on this part:

not a fan of using env_imp::getenv directly here, when this is clearly function that does a small modification to the output of var_os

Some(s) => s.into_string().map_err(VarError::NotUnicode),
None => Err(VarError::NotPresent),
}
env_imp::getenv(key).ok_or(VarError::NotPresent)?.into_string().map_err(VarError::NotUnicode)
Copy link
Member

Choose a reason for hiding this comment

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

I'm not a fan of using env_imp::getenv directly here, when this is clearly function that does a small modification to the output of var_os. I suppose _var_os might be okay, but only if there was a benefit.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Not sure why env_imp::getenv is an issue, it’s one less indirection, avoids unnecessary generic var_os calls, and _var_os seems like it should be an inner function to var_os.

@jhpratt
Copy link
Member

jhpratt commented Jan 29, 2026

Looks like @hkBst is on top of reviewing things already.

r? hkBst

@rustbot
Copy link
Collaborator

rustbot commented Jan 29, 2026

Failed to set assignee to hkBst: invalid assignee

Note: Only org members with at least the repository "read" role, users with write permissions, or people who have commented on the PR may be assigned.

@jhpratt
Copy link
Member

jhpratt commented Jan 29, 2026

Well, let me know when you think it's good to go and I can approve it on your behalf 🙂

@hkBst
Copy link
Member

hkBst commented Jan 29, 2026

Well, let me know when you think it's good to go and I can approve it on your behalf 🙂

Sure thing!

@rustbot author

@rustbot rustbot removed the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. label Jan 29, 2026
@rustbot
Copy link
Collaborator

rustbot commented Jan 29, 2026

Reminder, once the PR becomes ready for a review, use @rustbot ready.

@rustbot rustbot added the S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. label Jan 29, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. T-libs Relevant to the library team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants