openapistack / openapi-client-axios

JavaScript client library for consuming OpenAPI-enabled APIs with axios
https://openapistack.co
MIT License
556 stars 67 forks source link

Project Fetches YAML File Locally in Windows 11 Environment, Returns ECONNREFUSED Error #166

Open defremont opened 1 year ago

defremont commented 1 year ago

Hello, I just wanted to express my appreciation for the work you've done with this library!

I'm currently attempting to use it in a Windows 11 environment. Interestingly, the project operates without issue when executed on Ubuntu or when the JSON OpenAPI definition is directly passed into the 'definition' parameter. However, I've run into an issue on Windows where it attempts to fetch the YAML file at the following location: _currentUrl: 'http://localhost/src/utils/API_staging.yaml', Returning:

AxiosError: connect ECONNREFUSED ::1:80 ...... cause: Error: connect ECONNREFUSED ::1:80 at TCPConnectWrap.afterConnect [as oncomplete] (node:net:1494:16) { errno: -4078, code: 'ECONNREFUSED', syscall: 'connect', address: '::1', port: 80 }

I suspect there may be something I'm overlooking.

For reference, here's the content of my api.js file:


const OpenAPIClientAxios = require('openapi-client-axios').default

const api = new OpenAPIClientAxios({
  definition: process.env.OPENAPI_DEFINITION_FILE,
  strict: true,
  withServer: 0,
  axiosConfigDefaults: {
    withCredentials: true,
    headers: {
      'X-Api-Key': process.env.API_KEY,
      'Cache-Control': 'no-cache',
    },
  },
})
api.init()
module.exports = { api }

This is my .env:


# .env
API_KEY=staging-xxxx

OPENAPI_DEFINITION_FILE='.src/utils/API_staging.yaml'

Output:

AxiosError: connect ECONNREFUSED ::1:80 at AxiosError.from (D:\JOB\xxx\test2\xx-app-server\node_modules\axios\dist\node\axios.cjs:836:14) at RedirectableRequest.handleRequestError (D:\JOB\xxx\test2\xx-app-server\node_modules\axios\dist\node\axios.cjs:3010:25) at RedirectableRequest.emit (node:events:513:28) at eventHandlers. (D:\JOB\xxx\test2\xx-app-server\node_modules\follow-redirects\index.js:14:24) at ClientRequest.emit (node:events:513:28) at Socket.socketErrorListener (node:_http_client:502:9) at Socket.emit (node:events:513:28) at emitErrorNT (node:internal/streams/destroy:151:8) at emitErrorCloseNT (node:internal/streams/destroy:116:3) at process.processTicksAndRejections (node:internal/process/task_queues:82:21) { port: 80, address: '::1', syscall: 'connect', code: 'ECONNREFUSED', errno: -4078, config: { transitional: { silentJSONParsing: true, forcedJSONParsing: true, clarifyTimeoutError: false }, adapter: [ 'xhr', 'http' ], transformRequest: [ [Function: transformRequest] ], transformResponse: [ [Function: transformResponse] ], timeout: 0, xsrfCookieName: 'XSRF-TOKEN', xsrfHeaderName: 'X-XSRF-TOKEN', maxContentLength: -1, maxBodyLength: -1, env: { FormData: [Function: FormData] { LINE_BREAK: '\r\n', DEFAULT_CONTENT_TYPE: 'application/octet-stream' }, Blob: [class Blob] }, validateStatus: [Function: validateStatus], headers: AxiosHeaders { Accept: 'application/json, text/plain, /', 'X-Api-Key': 'staging-xxxx', 'Cache-Control': 'no-cache', 'User-Agent': 'axios/1.4.0', 'Accept-Encoding': 'gzip, compress, deflate, br' }, withCredentials: true, method: 'get', url: './API_staging.yaml', data: undefined }, request: <ref *2> Writable { _writableState: WritableState { objectMode: false, highWaterMark: 16384, finalCalled: false, needDrain: false, ending: false, ended: false, finished: false, destroyed: false, decodeStrings: true, defaultEncoding: 'utf8', length: 0, writing: false, corked: 0, sync: true, bufferProcessing: false, onwrite: [Function: bound onwrite], writecb: null, writelen: 0, afterWriteTickInfo: null, buffered: [], bufferedIndex: 0, allBuffers: true, allNoop: true, pendingcb: 0, constructed: true, prefinished: false, errorEmitted: false, emitClose: true, autoDestroy: true, errored: null, closed: false, closeEmitted: false,

},
_events: [Object: null prototype] {
  response: [Function: handleResponse],
  error: [Function: handleRequestError],
  socket: [Function: handleRequestSocket]
},
_eventsCount: 3,
_maxListeners: undefined,
_options: {
  maxRedirects: 21,
  maxBodyLength: Infinity,
  protocol: 'http:',
  path: '/API_staging.yaml',
  method: 'GET',
  headers: [Object: null prototype] {
    Accept: 'application/json, text/plain, */*',
    'X-Api-Key': 'staging-xxxx',
    'Cache-Control': 'no-cache',
    'User-Agent': 'axios/1.4.0',
    'Accept-Encoding': 'gzip, compress, deflate, br'
  },
  agents: { http: undefined, https: undefined },
  auth: undefined,
  family: undefined,
  lookup: undefined,
  beforeRedirect: [Function: dispatchBeforeRedirect],
  beforeRedirects: { proxy: [Function: beforeRedirect] },
  hostname: 'localhost',
  port: '',
  agent: undefined,
  nativeProtocols: {
    'http:': {
      _connectionListener: [Function: connectionListener],
      METHODS: [
        'ACL',         'BIND',       'CHECKOUT',
        'CONNECT',     'COPY',       'DELETE',
        'GET',         'HEAD',       'LINK',
        'LOCK',        'M-SEARCH',   'MERGE',
        'MKACTIVITY',  'MKCALENDAR', 'MKCOL',
        'MOVE',        'NOTIFY',     'OPTIONS',
        'PATCH',       'POST',       'PROPFIND',
        'PROPPATCH',   'PURGE',      'PUT',
        'REBIND',      'REPORT',     'SEARCH',
        'SOURCE',      'SUBSCRIBE',  'TRACE',
        'UNBIND',      'UNLINK',     'UNLOCK',
        'UNSUBSCRIBE'
      ],
      STATUS_CODES: {
        '100': 'Continue',
        '101': 'Switching Protocols',
        '102': 'Processing',
        '103': 'Early Hints',
        '200': 'OK',
        '201': 'Created',
        '202': 'Accepted',
        '203': 'Non-Authoritative Information',
        '204': 'No Content',
        '205': 'Reset Content',
        '206': 'Partial Content',
        '207': 'Multi-Status',
        '208': 'Already Reported',
        '226': 'IM Used',
        '300': 'Multiple Choices',
        '301': 'Moved Permanently',
        '302': 'Found',
        '303': 'See Other',
        '304': 'Not Modified',
        '305': 'Use Proxy',
        '307': 'Temporary Redirect',
        '308': 'Permanent Redirect',
        '400': 'Bad Request',
        '401': 'Unauthorized',
        '402': 'Payment Required',
        '403': 'Forbidden',
        '404': 'Not Found',
        '405': 'Method Not Allowed',
        '406': 'Not Acceptable',
        '407': 'Proxy Authentication Required',
        '408': 'Request Timeout',
        '409': 'Conflict',
        '410': 'Gone',
        '411': 'Length Required',
        '412': 'Precondition Failed',
        '413': 'Payload Too Large',
        '414': 'URI Too Long',
        '415': 'Unsupported Media Type',
        '416': 'Range Not Satisfiable',
        '417': 'Expectation Failed',
        '418': "I'm a Teapot",
        '421': 'Misdirected Request',
        '422': 'Unprocessable Entity',
        '423': 'Locked',
        '424': 'Failed Dependency',
        '425': 'Too Early',
        '426': 'Upgrade Required',
        '428': 'Precondition Required',
        '429': 'Too Many Requests',
        '431': 'Request Header Fields Too Large',
        '451': 'Unavailable For Legal Reasons',
        '500': 'Internal Server Error',
        '501': 'Not Implemented',
        '502': 'Bad Gateway',
        '503': 'Service Unavailable',
        '504': 'Gateway Timeout',
        '505': 'HTTP Version Not Supported',
        '506': 'Variant Also Negotiates',
        '507': 'Insufficient Storage',
        '508': 'Loop Detected',
        '509': 'Bandwidth Limit Exceeded',
        '510': 'Not Extended',
        '511': 'Network Authentication Required'
      },
      Agent: [Function: Agent] { defaultMaxSockets: Infinity },
      ClientRequest: [Function: ClientRequest],
      IncomingMessage: [Function: IncomingMessage],
      OutgoingMessage: [Function: OutgoingMessage],
      Server: [Function: Server],
      ServerResponse: [Function: ServerResponse],
      createServer: [Function: createServer],
      validateHeaderName: [Function: __node_internal_],
      validateHeaderValue: [Function: __node_internal_],
      get: [Function: get],
      request: [Function: request],
      setMaxIdleHTTPParsers: [Function: setMaxIdleHTTPParsers],
      maxHeaderSize: [Getter],
      globalAgent: [Getter/Setter]
    },
    'https:': {
      Agent: [Function: Agent],
      globalAgent: Agent {
        _events: [Object: null prototype],
        _eventsCount: 2,
        _maxListeners: undefined,
        defaultPort: 443,
        protocol: 'https:',
        options: [Object: null prototype],
        requests: [Object: null prototype] {},
        sockets: [Object: null prototype] {},
        freeSockets: [Object: null prototype] {},
        keepAliveMsecs: 1000,
        keepAlive: false,
        maxSockets: Infinity,
        maxFreeSockets: 256,
        scheduling: 'lifo',
        maxTotalSockets: Infinity,
        totalSocketCount: 0,
        maxCachedSessions: 100,
        _sessionCache: [Object],
        [Symbol(kCapture)]: false
      },
      Server: [Function: Server],
      createServer: [Function: createServer],
      get: [Function: get],
      request: [Function: request]
    }
  },
  pathname: '/API_staging.yaml'
},
_ended: true,
_ending: true,
_redirectCount: 0,
_redirects: [],
_requestBodyLength: 0,
_requestBodyBuffers: [],
_onNativeResponse: [Function (anonymous)],
_currentRequest: <ref *1> ClientRequest {
  _events: [Object: null prototype] {
    response: [Function: bound onceWrapper] {
      listener: [Function (anonymous)]
    },
    abort: [Function (anonymous)],
    aborted: [Function (anonymous)],
    connect: [Function (anonymous)],
    error: [Function (anonymous)],
    socket: [Function (anonymous)],
    timeout: [Function (anonymous)]
  },
  _eventsCount: 7,
  _maxListeners: undefined,
  outputData: [],
  outputSize: 0,
  writable: true,
  destroyed: false,
  _last: true,
  chunkedEncoding: false,
  shouldKeepAlive: false,
  maxRequestsOnConnectionReached: false,
  _defaultKeepAlive: true,
  useChunkedEncodingByDefault: false,
  sendDate: false,
  _removedConnection: false,
  _removedContLen: false,
  _removedTE: false,
  strictContentLength: false,
  _contentLength: 0,
  _hasBody: true,
  _trailer: '',
  finished: true,
  _headerSent: true,
  _closed: false,
  socket: Socket {
    connecting: false,
    _hadError: true,
    _parent: null,
    _host: 'localhost',
    _closeAfterHandlingError: false,
    _readableState: ReadableState {
      objectMode: false,
      highWaterMark: 16384,
      buffer: BufferList { head: null, tail: null, length: 0 },
      length: 0,
      pipes: [],
      flowing: true,
      ended: false,
      endEmitted: false,
      reading: true,
      constructed: true,
      sync: false,
      needReadable: true,
      emittedReadable: false,
      readableListening: false,
      resumeScheduled: false,
      errorEmitted: true,
      emitClose: false,
      autoDestroy: true,
      destroyed: true,
      errored: Error: connect ECONNREFUSED ::1:80
          at TCPConnectWrap.afterConnect [as oncomplete] (node:net:1494:16) {
        errno: -4078,
        code: 'ECONNREFUSED',
        syscall: 'connect',
        address: '::1',
        port: 80
      },
      closed: true,
      closeEmitted: true,
      defaultEncoding: 'utf8',
      awaitDrainWriters: null,
      multiAwaitDrain: false,
      readingMore: false,
      dataEmitted: false,
      decoder: null,
      encoding: null,
      [Symbol(kPaused)]: false
    },
    _events: [Object: null prototype] {
      end: [Function: onReadableStreamEnd],
      connect: [ [Function], [Function], [Function] ],
      free: [Function: onFree],
      close: [
        [Function: onClose],
        [Function: socketCloseListener],
        [Function]
      ],
      timeout: [Function: onTimeout],
      agentRemove: [Function: onRemove],
      error: [Function: socketErrorListener],
      drain: [Function: ondrain]
    },
    _eventsCount: 8,
    _maxListeners: undefined,
    _writableState: WritableState {
      objectMode: false,
      highWaterMark: 16384,
      finalCalled: false,
      needDrain: false,
      ending: false,
      ended: false,
      finished: false,
      destroyed: true,
      decodeStrings: false,
      defaultEncoding: 'utf8',
      length: 286,
      writing: true,
      corked: 0,
      sync: false,
      bufferProcessing: false,
      onwrite: [Function: bound onwrite],
      writecb: [Function: bound onFinish],
      writelen: 286,
      afterWriteTickInfo: null,
      buffered: [],
      bufferedIndex: 0,
      allBuffers: true,
      allNoop: true,
      pendingcb: 1,
      constructed: true,
      prefinished: false,
      errorEmitted: true,
      emitClose: false,
      autoDestroy: true,
      errored: Error: connect ECONNREFUSED ::1:80
          at TCPConnectWrap.afterConnect [as oncomplete] (node:net:1494:16) {
        errno: -4078,
        code: 'ECONNREFUSED',
        syscall: 'connect',
        address: '::1',
        port: 80
      },
      closed: true,
      closeEmitted: true,
      [Symbol(kOnFinished)]: []
    },
    allowHalfOpen: false,
    _sockname: null,
    _pendingData: 'GET /API_staging.yaml HTTP/1.1\r\n' +
      'Accept: application/json, text/plain, */*\r\n' +
      'X-Api-Key: staging-xxxx\r\n' +
      'Cache-Control: no-cache\r\n' +
      'User-Agent: axios/1.4.0\r\n' +
      'Accept-Encoding: gzip, compress, deflate, br\r\n' +
      'Host: localhost\r\n' +
      'Connection: close\r\n' +
      '\r\n',
    _pendingEncoding: 'latin1',
    server: null,
    _server: null,
    parser: null,
    _httpMessage: [Circular *1],
    [Symbol(async_id_symbol)]: 14,
    [Symbol(kHandle)]: null,
    [Symbol(lastWriteQueueSize)]: 0,
    [Symbol(timeout)]: null,
    [Symbol(kBuffer)]: null,
    [Symbol(kBufferCb)]: null,
    [Symbol(kBufferGen)]: null,
    [Symbol(kCapture)]: false,
    [Symbol(kSetNoDelay)]: true,
    [Symbol(kSetKeepAlive)]: true,
    [Symbol(kSetKeepAliveInitialDelay)]: 60,
    [Symbol(kBytesRead)]: 0,
    [Symbol(kBytesWritten)]: 0
  },
  _header: 'GET /API_staging.yaml HTTP/1.1\r\n' +
    'Accept: application/json, text/plain, */*\r\n' +
    'X-Api-Key: staging-xxxx\r\n' +
    'Cache-Control: no-cache\r\n' +
    'User-Agent: axios/1.4.0\r\n' +
    'Accept-Encoding: gzip, compress, deflate, br\r\n' +
    'Host: localhost\r\n' +
    'Connection: close\r\n' +
    '\r\n',
  _keepAliveTimeout: 0,
  _onPendingData: [Function: nop],
  agent: Agent {
    _events: [Object: null prototype] {
      free: [Function (anonymous)],
      newListener: [Function: maybeEnableKeylog]
    },
    _eventsCount: 2,
    _maxListeners: undefined,
    defaultPort: 80,
    protocol: 'http:',
    options: [Object: null prototype] { noDelay: true, path: null },
    requests: [Object: null prototype] {},
    sockets: [Object: null prototype] {
      'localhost:80:': [ [Socket] ],
      'localhost:5984:': [ [Socket] ]
    },
    freeSockets: [Object: null prototype] {},
    keepAliveMsecs: 1000,
    keepAlive: false,
    maxSockets: Infinity,
    maxFreeSockets: 256,
    scheduling: 'lifo',
    maxTotalSockets: Infinity,
    totalSocketCount: 2,
    [Symbol(kCapture)]: false
  },
  socketPath: undefined,
  method: 'GET',
  maxHeaderSize: undefined,
  insecureHTTPParser: undefined,
  joinDuplicateHeaders: undefined,
  path: '/API_staging.yaml',
  _ended: false,
  res: null,
  aborted: false,
  timeoutCb: null,
  upgradeOrConnect: false,
  parser: null,
  maxHeadersCount: null,
  reusedSocket: false,
  host: 'localhost',
  protocol: 'http:',
  _redirectable: [Circular *2],
  [Symbol(kCapture)]: false,
  [Symbol(kBytesWritten)]: 0,
  [Symbol(kNeedDrain)]: false,
  [Symbol(corked)]: 0,
  [Symbol(kOutHeaders)]: [Object: null prototype] {
    accept: [ 'Accept', 'application/json, text/plain, */*' ],
    'X-Api-Key': [
      'X-Api-Key',
      'staging-xxxx'
    ],
    'cache-control': [ 'Cache-Control', 'no-cache' ],
    'user-agent': [ 'User-Agent', 'axios/1.4.0' ],
    'accept-encoding': [ 'Accept-Encoding', 'gzip, compress, deflate, br' ],
    host: [ 'Host', 'localhost' ]
  },
  [Symbol(errored)]: null,
  [Symbol(kUniqueHeaders)]: null
},
_currentUrl: 'http://localhost/API_staging.yaml',
[Symbol(kCapture)]: false

}, cause: Error: connect ECONNREFUSED ::1:80 at TCPConnectWrap.afterConnect [as oncomplete] (node:net:1494:16) { errno: -4078, code: 'ECONNREFUSED', syscall: 'connect', address: '::1', port: 80 } }

defremont commented 1 year ago

This also works:

definition: yaml.load( fs.readFileSync(process.env.OPENAPI_DEFINITION_FILE, "utf8") ),

But I'm still wondering why the other way won't work on Windows 11.