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

os: add homedir() #1791

Merged
merged 1 commit into from
Jun 6, 2015
Merged
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
4 changes: 4 additions & 0 deletions doc/api/os.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,10 @@ Use `require('os')` to access this module.

Returns the operating system's default directory for temporary files.

## os.homedir()

Returns the home directory of the current user.

## os.endianness()

Returns the endianness of the CPU. Possible values are `'BE'` for big endian
Expand Down
2 changes: 2 additions & 0 deletions lib/os.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ exports.cpus = binding.getCPUs;
exports.type = binding.getOSType;
exports.release = binding.getOSRelease;
exports.networkInterfaces = binding.getInterfaceAddresses;
exports.homedir = binding.getHomeDirectory;


exports.arch = function() {
return process.arch;
Expand Down
21 changes: 21 additions & 0 deletions src/node_os.cc
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
#endif // __MINGW32__

#ifdef __POSIX__
# include <limits.h> // PATH_MAX on Solaris.
# include <netdb.h> // MAXHOSTNAMELEN on Solaris.
# include <unistd.h> // gethostname, sysconf
# include <sys/param.h> // MAXHOSTNAMELEN on Linux and the BSDs.
Expand Down Expand Up @@ -271,6 +272,25 @@ static void GetInterfaceAddresses(const FunctionCallbackInfo<Value>& args) {
}


static void GetHomeDirectory(const FunctionCallbackInfo<Value>& args) {
Environment* env = Environment::GetCurrent(args);
char buf[PATH_MAX];

size_t len = sizeof(buf);
const int err = uv_os_homedir(buf, &len);

if (err) {
return env->ThrowUVException(err, "uv_os_homedir");
}

Local<String> home = String::NewFromUtf8(env->isolate(),
buf,
String::kNormalString,
len);
args.GetReturnValue().Set(home);
}


void Initialize(Handle<Object> target,
Handle<Value> unused,
Handle<Context> context) {
Expand All @@ -284,6 +304,7 @@ void Initialize(Handle<Object> target,
env->SetMethod(target, "getOSType", GetOSType);
env->SetMethod(target, "getOSRelease", GetOSRelease);
env->SetMethod(target, "getInterfaceAddresses", GetInterfaceAddresses);
env->SetMethod(target, "getHomeDirectory", GetHomeDirectory);
target->Set(FIXED_ONE_BYTE_STRING(env->isolate(), "isBigEndian"),
Boolean::New(env->isolate(), IsBigEndian()));
}
Expand Down
1 change: 1 addition & 0 deletions test/common.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ exports.fixturesDir = path.join(exports.testDir, 'fixtures');
exports.libDir = path.join(exports.testDir, '../lib');
exports.tmpDirName = 'tmp';
exports.PORT = +process.env.NODE_COMMON_PORT || 12346;
exports.isWindows = process.platform === 'win32';

if (process.env.TEST_THREAD_ID) {
// Distribute ports in parallel tests
Expand Down
30 changes: 30 additions & 0 deletions test/parallel/test-os-homedir-no-envvar.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
'use strict';
var common = require('../common');
var assert = require('assert');
var cp = require('child_process');
var os = require('os');
var path = require('path');


if (process.argv[2] === 'child') {
if (common.isWindows)
assert.equal(process.env.USERPROFILE, undefined);
else
assert.equal(process.env.HOME, undefined);

var home = os.homedir();

assert.ok(typeof home === 'string');
assert.ok(home.indexOf(path.sep) !== -1);
} else {
if (common.isWindows)
delete process.env.USERPROFILE;
else
delete process.env.HOME;

var child = cp.spawnSync(process.execPath, [__filename, 'child'], {
env: process.env
});

assert.equal(child.status, 0);
}
22 changes: 21 additions & 1 deletion test/parallel/test-os.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,13 @@
var common = require('../common');
var assert = require('assert');
var os = require('os');
var path = require('path');


process.env.TMPDIR = '/tmpdir';
process.env.TMP = '/tmp';
process.env.TEMP = '/temp';
if (process.platform === 'win32') {
if (common.isWindows) {
assert.equal(os.tmpdir(), '/temp');
process.env.TEMP = '';
assert.equal(os.tmpdir(), '/tmp');
Expand Down Expand Up @@ -101,3 +102,22 @@ switch (platform) {

var EOL = os.EOL;
assert.ok(EOL.length > 0);


var home = os.homedir();

console.log('homedir = ' + home);
assert.ok(typeof home === 'string');
assert.ok(home.indexOf(path.sep) !== -1);

if (common.isWindows && process.env.USERPROFILE) {
assert.equal(home, process.env.USERPROFILE);
delete process.env.USERPROFILE;
assert.ok(os.homedir().indexOf(path.sep) !== -1);
process.env.USERPROFILE = home;
} else if (!common.isWindows && process.env.HOME) {
assert.equal(home, process.env.HOME);
delete process.env.HOME;
assert.ok(os.homedir().indexOf(path.sep) !== -1);
process.env.HOME = home;
}
Copy link
Member

Choose a reason for hiding this comment

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

Maybe as an extra check delete HOME / USERPROFILE from the env and check that os.homedir() still returns something.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

@bnoordhuis updated based on your feedback. I added a check that modifies the existing environment. I also added a new test that spawns a child process without the appropriate environment variables.