os: implement os.environ() (part 2/2) (#3971)
parent
877b474fe1
commit
7036ca55e6
|
@ -0,0 +1,80 @@
|
||||||
|
// Copyright (c) 2019-2020 Alexander Medvednikov. All rights reserved.
|
||||||
|
// Use of this source code is governed by an MIT license
|
||||||
|
// that can be found in the LICENSE file.
|
||||||
|
module os
|
||||||
|
|
||||||
|
fn C.getenv(byteptr) &char
|
||||||
|
// C.GetEnvironmentStringsW & C.FreeEnvironmentStringsW are defined only on windows
|
||||||
|
fn C.GetEnvironmentStringsW() &u16
|
||||||
|
|
||||||
|
|
||||||
|
fn C.FreeEnvironmentStringsW(&u16) int
|
||||||
|
// `getenv` returns the value of the environment variable named by the key.
|
||||||
|
pub fn getenv(key string) string {
|
||||||
|
$if windows {
|
||||||
|
s := C._wgetenv(key.to_wide())
|
||||||
|
if s == 0 {
|
||||||
|
return ''
|
||||||
|
}
|
||||||
|
return string_from_wide(s)
|
||||||
|
} $else {
|
||||||
|
s := C.getenv(key.str)
|
||||||
|
if s == 0 {
|
||||||
|
return ''
|
||||||
|
}
|
||||||
|
// NB: C.getenv *requires* that the result be copied.
|
||||||
|
return cstring_to_vstring(byteptr(s))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// os.setenv sets the value of an environment variable with `name` to `value`.
|
||||||
|
pub fn setenv(name string, value string, overwrite bool) int {
|
||||||
|
$if windows {
|
||||||
|
format := '$name=$value'
|
||||||
|
if overwrite {
|
||||||
|
return C._putenv(format.str)
|
||||||
|
}
|
||||||
|
return -1
|
||||||
|
} $else {
|
||||||
|
return C.setenv(name.str, value.str, overwrite)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// os.unsetenv clears an environment variable with `name`.
|
||||||
|
pub fn unsetenv(name string) int {
|
||||||
|
$if windows {
|
||||||
|
format := '${name}='
|
||||||
|
return C._putenv(format.str)
|
||||||
|
} $else {
|
||||||
|
return C.unsetenv(name.str)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// See: https://linux.die.net/man/5/environ for unix platforms.
|
||||||
|
// See: https://docs.microsoft.com/bg-bg/windows/win32/api/processenv/nf-processenv-getenvironmentstrings
|
||||||
|
// os.environ returns a map of all the current environment variables
|
||||||
|
pub fn environ() map[string]string {
|
||||||
|
mut res := map[string]string
|
||||||
|
$if windows {
|
||||||
|
mut estrings := C.GetEnvironmentStringsW()
|
||||||
|
mut eline := ''
|
||||||
|
for c := estrings; *c != 0; c = c + eline.len + 1 {
|
||||||
|
eline = string_from_wide(c)
|
||||||
|
eq_index := eline.index_byte(`=`)
|
||||||
|
if eq_index > 0 {
|
||||||
|
res[eline[0..eq_index]] = eline[eq_index + 1..]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
C.FreeEnvironmentStringsW(estrings)
|
||||||
|
} $else {
|
||||||
|
e := &byteptr(&C.environ)
|
||||||
|
for i := 0; !isnil(e[i]); i++ {
|
||||||
|
eline := cstring_to_vstring(e[i])
|
||||||
|
eq_index := eline.index_byte(`=`)
|
||||||
|
if eq_index > 0 {
|
||||||
|
res[eline[0..eq_index]] = eline[eq_index + 1..]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res
|
||||||
|
}
|
|
@ -0,0 +1,36 @@
|
||||||
|
import os
|
||||||
|
|
||||||
|
fn test_getenv() {
|
||||||
|
// VEXE is set by the V builtin test runner
|
||||||
|
assert os.getenv('VEXE').len > 0
|
||||||
|
assert os.getenv('PATH').len > 0
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_setenv() {
|
||||||
|
os.setenv('foo', 'bar', true)
|
||||||
|
assert os.getenv('foo') == 'bar'
|
||||||
|
// `setenv` should not set if `overwrite` is false
|
||||||
|
os.setenv('foo', 'bar2', false)
|
||||||
|
assert os.getenv('foo') == 'bar'
|
||||||
|
// `setenv` should overwrite if `overwrite` is true
|
||||||
|
os.setenv('foo', 'bar2', true)
|
||||||
|
assert os.getenv('foo') == 'bar2'
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_unsetenv() {
|
||||||
|
os.setenv('foo', 'bar', true)
|
||||||
|
os.unsetenv('foo')
|
||||||
|
assert os.getenv('foo') == ''
|
||||||
|
}
|
||||||
|
|
||||||
|
fn test_environ() {
|
||||||
|
os.setenv('myvar1', 'bar1', true)
|
||||||
|
os.setenv('myvar2', 'bar2', true)
|
||||||
|
assert os.getenv('myvar1') == 'bar1'
|
||||||
|
assert os.getenv('myvar2') == 'bar2'
|
||||||
|
assert os.getenv('myvar_not_defined') == ''
|
||||||
|
all := os.environ()
|
||||||
|
assert all['myvar1'] == 'bar1'
|
||||||
|
assert all['myvar2'] == 'bar2'
|
||||||
|
assert all['myvar_not_defined'] == ''
|
||||||
|
}
|
42
vlib/os/os.v
42
vlib/os/os.v
|
@ -65,9 +65,6 @@ fn C.getline(voidptr, voidptr, voidptr) int
|
||||||
fn C.ftell(fp voidptr) int
|
fn C.ftell(fp voidptr) int
|
||||||
|
|
||||||
|
|
||||||
fn C.getenv(byteptr) &char
|
|
||||||
|
|
||||||
|
|
||||||
fn C.sigaction(int, voidptr, int)
|
fn C.sigaction(int, voidptr, int)
|
||||||
|
|
||||||
|
|
||||||
|
@ -507,45 +504,6 @@ pub fn sigint_to_signal_name(si int) string {
|
||||||
return 'unknown'
|
return 'unknown'
|
||||||
}
|
}
|
||||||
|
|
||||||
// `getenv` returns the value of the environment variable named by the key.
|
|
||||||
pub fn getenv(key string) string {
|
|
||||||
$if windows {
|
|
||||||
s := C._wgetenv(key.to_wide())
|
|
||||||
if s == 0 {
|
|
||||||
return ''
|
|
||||||
}
|
|
||||||
return string_from_wide(s)
|
|
||||||
} $else {
|
|
||||||
s := C.getenv(key.str)
|
|
||||||
if s == 0 {
|
|
||||||
return ''
|
|
||||||
}
|
|
||||||
// NB: C.getenv *requires* that the result be copied.
|
|
||||||
return cstring_to_vstring(byteptr(s))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn setenv(name string, value string, overwrite bool) int {
|
|
||||||
$if windows {
|
|
||||||
format := '$name=$value'
|
|
||||||
if overwrite {
|
|
||||||
return C._putenv(format.str)
|
|
||||||
}
|
|
||||||
return -1
|
|
||||||
} $else {
|
|
||||||
return C.setenv(name.str, value.str, overwrite)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn unsetenv(name string) int {
|
|
||||||
$if windows {
|
|
||||||
format := '${name}='
|
|
||||||
return C._putenv(format.str)
|
|
||||||
} $else {
|
|
||||||
return C.unsetenv(name.str)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const (
|
const (
|
||||||
F_OK = 0
|
F_OK = 0
|
||||||
X_OK = 1
|
X_OK = 1
|
||||||
|
|
|
@ -8,25 +8,6 @@ fn testsuite_end() {
|
||||||
cleanup_leftovers()
|
cleanup_leftovers()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn test_setenv() {
|
|
||||||
os.setenv('foo', 'bar', true)
|
|
||||||
assert os.getenv('foo') == 'bar'
|
|
||||||
|
|
||||||
// `setenv` should not set if `overwrite` is false
|
|
||||||
os.setenv('foo', 'bar2', false)
|
|
||||||
assert os.getenv('foo') == 'bar'
|
|
||||||
|
|
||||||
// `setenv` should overwrite if `overwrite` is true
|
|
||||||
os.setenv('foo', 'bar2', true)
|
|
||||||
assert os.getenv('foo') == 'bar2'
|
|
||||||
}
|
|
||||||
|
|
||||||
fn test_unsetenv() {
|
|
||||||
os.setenv('foo', 'bar', true)
|
|
||||||
os.unsetenv('foo')
|
|
||||||
assert os.getenv('foo') == ''
|
|
||||||
}
|
|
||||||
|
|
||||||
fn test_open_file() {
|
fn test_open_file() {
|
||||||
filename := './test1.txt'
|
filename := './test1.txt'
|
||||||
hello := 'hello world!'
|
hello := 'hello world!'
|
||||||
|
|
Loading…
Reference in New Issue