繁体   English   中英

Node 的控制台没有显示所有对象属性......这是预期的行为吗?

[英]Node's console is not showing all the object properties ... is this expected behavior?

我做了一个

  console.log(myURL);

并且没有看到扩展属性

  console.log(myURL.extension);

但是如果我自己登录它,它会正确显示该值。

found 是一个这样创建的 URL 对象:

  const url = require('url');
  let myURL = new URL(test);

添加了缺失的属性:

  myURL.extension = test.split('.').pop();

输出如下所示:

URL {
  href: 'https://www.imdb.com/favicon.ico',
  origin: 'https://www.imdb.com',
  protocol: 'https:',
  username: '',
  password: '',
  host: 'www.imdb.com',
  hostname: 'www.imdb.com',
  port: '',
  pathname: '/favicon.ico',
  search: '',
  searchParams: URLSearchParams {},
  hash: ''
}

示例代码:

const url = require('url');
const test = 'https://www.imdb.com/favicon.ico';
let myURL = new URL(test);
myURL.extension = test.split('.').pop();
console.log(myURL);

这种行为的原因是因为URLprototype定义了一个util.inspect.custom覆盖。 例如在 Node.js v12.11.0 中,它是这样定义的:

> console.log(myURL[util.inspect.custom])

[inspect.custom](depth, opts) {
  if (this == null ||
      Object.getPrototypeOf(this[context]) !== URLContext.prototype) {
    throw new ERR_INVALID_THIS('URL');
  }

  if (typeof depth === 'number' && depth < 0)
    return this;

  const ctor = getConstructorOf(this);

  const obj = Object.create({
    constructor: ctor === null ? URL : ctor
  });

  obj.href = this.href;
  obj.origin = this.origin;
  obj.protocol = this.protocol;
  obj.username = this.username;
  obj.password = this.password;
  obj.host = this.host;
  obj.hostname = this.hostname;
  obj.port = this.port;
  obj.pathname = this.pathname;
  obj.search = this.search;
  obj.searchParams = this.searchParams;
  obj.hash = this.hash;

  if (opts.showHidden) {
    obj.cannotBeBase = this[cannotBeBase];
    obj.special = this[special];
    obj[context] = this[context];
  }

  return inspect(obj, opts);
}

如果您真的关心输出格式,您可以覆盖此行为并将extension属性作为 getter 添加到URL类的prototype

const { URL } = require('url');
const { inspect } = require('util');

Object.defineProperty(URL.prototype, 'extension', {
  enumerable: true,
  configurable: true,
  get() { return this.pathname.split('.').pop(); }
});

URL.prototype[inspect.custom] = function(depth, opts) {
  if (typeof depth === 'number' && depth < 0) return this;

  const keys = Object.keys(URL.prototype).filter(key => typeof this[key] !== 'function');
  const obj = Object.create({ constructor: URL });
  Object.assign(obj, ...keys.map(key => ({ [key]: this[key] })));
  return inspect(obj, opts);
};

然后您的输出格式将如下所示:

> new URL('https://www.imdb.com/favicon.ico')
URL {
  href: 'https://www.imdb.com/favicon.ico',
  origin: 'https://www.imdb.com',
  protocol: 'https:',
  username: '',
  password: '',
  host: 'www.imdb.com',
  hostname: 'www.imdb.com',
  port: '',
  pathname: '/favicon.ico',
  search: '',
  searchParams: URLSearchParams {},
  hash: '',
  extension: 'ico'
}

但是,如果您不太在意,那么您可以接受您看到的输出格式是预期的行为,并且您可以像通常在任何其他对象上一样访问extension属性。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM