summaryrefslogtreecommitdiff
path: root/deps/npm/lib/utils/error-handler.js
diff options
context:
space:
mode:
Diffstat (limited to 'deps/npm/lib/utils/error-handler.js')
-rw-r--r--deps/npm/lib/utils/error-handler.js264
1 files changed, 264 insertions, 0 deletions
diff --git a/deps/npm/lib/utils/error-handler.js b/deps/npm/lib/utils/error-handler.js
new file mode 100644
index 0000000000..af52e61697
--- /dev/null
+++ b/deps/npm/lib/utils/error-handler.js
@@ -0,0 +1,264 @@
+
+module.exports = errorHandler
+
+var cbCalled = false
+ , log = require("./log.js")
+ , npm = require("../npm.js")
+ , rm = require("rimraf")
+ , constants = require("constants")
+ , itWorked = false
+ , path = require("path")
+ , ini = require("./ini.js")
+ , wroteLogFile = false
+
+
+process.on("exit", function (code) {
+ // console.error("exit", code)
+ if (!ini.resolved) return
+ if (code) itWorked = false
+ if (itWorked) log("ok")
+ else {
+ if (!cbCalled) {
+ log.error("cb() never called!\n ")
+ }
+ if (wroteLogFile) {
+ log.error([""
+ ,"Additional logging details can be found in:"
+ ," " + path.resolve("npm-debug.log")
+ ].join("\n"))
+ wroteLogFile = false
+ }
+ log.win("not ok")
+ }
+ itWorked = false // ready for next exit
+})
+
+function errorHandler (er) {
+ // console.error("errorHandler", er)
+ if (!ini.resolved) {
+ // logging won't work unless we pretend that it's ready
+ er = er || new Error("Exit prior to config file resolving.")
+ console.error(er.stack || er.message)
+ }
+
+ if (cbCalled) {
+ er = er || new Error("Callback called more than once.")
+ }
+
+ cbCalled = true
+ if (!er) return exit(0)
+ if (!(er instanceof Error)) {
+ log.error(er)
+ return exit(1, true)
+ }
+
+ var m = er.code || er.message.match(/^(?:Error: )?(E[A-Z]+)/)
+ if (m) {
+ m = m[1]
+ if (!constants[m] && !npm[m]) constants[m] = {}
+ er.errno = npm[m] || constants[m]
+ }
+
+ switch (er.errno) {
+ case "ECONNREFUSED":
+ case constants.ECONNREFUSED:
+ log.error(er)
+ log.error(["If you are using Cygwin, please set up your /etc/resolv.conf"
+ ,"See step 4 in this wiki page:"
+ ," http://github.com/ry/node/wiki/Building-node.js-on-Cygwin-%28Windows%29"
+ ,"If you are not using Cygwin, please report this"
+ ,"at <http://github.com/isaacs/npm/issues>"
+ ,"or email it to <npm-@googlegroups.com>"
+ ].join("\n"))
+ break
+
+ case "EACCES":
+ case "EPERM":
+ case constants.EACCES:
+ case constants.EPERM:
+ log.error(er)
+ log.error(["",
+ "Please use 'sudo' or log in as root to run this command."
+ ,""
+ ," sudo npm "
+ +npm.config.get("argv").original.map(JSON.stringify).join(" ")
+ ,""
+ ,"or set the 'unsafe-perm' config var to true."
+ ,""
+ ," npm config set unsafe-perm true"
+ ].join("\n"))
+ break
+
+ case npm.ELIFECYCLE:
+ er.code = "ELIFECYCLE"
+ log.error(er.message)
+ log.error(["","Failed at the "+er.pkgid+" "+er.stage+" script."
+ ,"This is most likely a problem with the "+er.pkgname+" package,"
+ ,"not with npm itself."
+ ,"Tell the author that this fails on your system:"
+ ," "+er.script
+ ,"You can get their info via:"
+ ," npm owner ls "+er.pkgname
+ ,"There is likely additional logging output above."
+ ].join("\n"))
+ break
+
+ case npm.EJSONPARSE:
+ er.code = "EJSONPARSE"
+ log.error(er.message)
+ log.error("File: "+er.file)
+ log.error(["Failed to parse package.json data."
+ ,"package.json must be actual JSON, not just JavaScript."
+ ,"","This is not a bug in npm."
+ ,"Tell the package author to fix their package.json file."
+ ].join("\n"), "JSON.parse")
+ break
+
+ case npm.E404:
+ er.code = "E404"
+ if (er.pkgid && er.pkgid !== "-") {
+ var msg = ["'"+er.pkgid+"' is not in the npm registry."
+ ,"You could maybe bug the author to publish it"]
+ if (er.pkgid.match(/^node[\.\-]|[\.\-]js$/)) {
+ var s = er.pkgid.replace(/^node[\.\-]|[\.\-]js$/g, "")
+ if (s !== er.pkgid) {
+ s = s.replace(/[^a-z0-9]/g, ' ')
+ msg.push("Maybe try 'npm search " + s + "'")
+ }
+ }
+ msg.push("Note that you can also install from a tarball or folder.")
+ log.error(msg.join("\n"), "404")
+ }
+ break
+
+ case npm.EPUBLISHCONFLICT:
+ er.code = "EPUBLISHCONFLICT"
+ log.error(["Cannot publish over existing version."
+ ,"Bump the 'version' field, set the --force flag, or"
+ ," npm unpublish '"+er.pkgid+"'"
+ ,"and try again"
+ ].join("\n"), "publish fail" )
+ break
+
+ case npm.EISGIT:
+ er.code = "EISGIT"
+ log.error([er.message
+ ," "+er.path
+ ,"Refusing to remove it. Update manually,"
+ ,"or move it out of the way first."
+ ].join("\n"), "git" )
+ break
+
+ case npm.ECYCLE:
+ er.code = "ECYCLE"
+ log.error([er.message
+ ,"While installing: "+er.pkgid
+ ,"Found a pathological dependency case that npm cannot solve."
+ ,"Please report this to the package author."
+ ].join("\n"))
+ break
+
+ case npm.ENOTSUP:
+ er.code = "ENOTSUP"
+ log.error([er.message
+ ,"Not compatible with your version of node/npm: "+er.pkgid
+ ,"Required: "+JSON.stringify(er.required)
+ ,"Actual: "
+ +JSON.stringify({npm:npm.version
+ ,node:npm.config.get("node-version")})
+ ].join("\n"))
+ break
+
+ case "EEXIST":
+ case constants.EEXIST:
+ log.error([er.message
+ ,"File exists: "+er.path
+ ,"Move it away, and try again."].join("\n"))
+ break
+
+ default:
+ log.error(er)
+ log.error(["Report this *entire* log at:"
+ ," <http://github.com/isaacs/npm/issues>"
+ ,"or email it to:"
+ ," <npm-@googlegroups.com>"
+ ].join("\n"))
+ break
+ }
+
+ var os = require("os")
+ log.error("")
+ log.error(os.type() + " " + os.release(), "System")
+ log.error(process.argv
+ .map(JSON.stringify).join(" "), "command")
+ log.error(process.cwd(), "cwd")
+ log.error(process.version, "node -v")
+ log.error(npm.version, "npm -v")
+
+ ; [ "file"
+ , "path"
+ , "type"
+ , "syscall"
+ , "fstream_path"
+ , "fstream_unc_path"
+ , "fstream_type"
+ , "fstream_class"
+ , "fstream_finish_call"
+ , "fstream_linkpath"
+ , "arguments"
+ , "code"
+ , "message"
+ ].forEach(function (k) {
+ if (er[k]) log.error(er[k], k)
+ })
+
+ if (er.fstream_stack) {
+ log.error(er.fstream_stack.join("\n"), "fstream_stack")
+ }
+
+ if (er.errno && typeof er.errno !== "object") log.error(er.errno, "errno")
+ exit(typeof er.errno === "number" ? er.errno : 1)
+}
+
+function exit (code, noLog) {
+ var doExit = npm.config.get("_exit")
+ log.verbose([code, doExit], "exit")
+ if (log.level === log.LEVEL.silent) noLog = true
+
+ if (code && !noLog) writeLogFile(reallyExit)
+ else rm("npm-debug.log", function () { rm(npm.tmp, reallyExit) })
+
+ function reallyExit() {
+ itWorked = !code
+ //if (!itWorked) {
+ if (!doExit) process.emit("exit", code)
+ else process.exit(code)
+ //}
+ }
+}
+
+var writingLogFile = false
+function writeLogFile (cb) {
+ if (writingLogFile) return cb()
+ writingLogFile = true
+ wroteLogFile = true
+
+ var fs = require("graceful-fs")
+ , fstr = fs.createWriteStream("npm-debug.log")
+ , util = require("util")
+
+ log.history.forEach(function (m) {
+ var lvl = log.LEVEL[m.level]
+ , pref = m.pref ? " " + m.pref : ""
+ , b = lvl + pref + " "
+ , eol = process.platform === "win32" ? "\r\n" : "\n"
+ , msg = typeof m.msg === "string" ? m.msg
+ : msg instanceof Error ? msg.stack || msg.message
+ : util.inspect(m.msg, 0, 4)
+ fstr.write(new Buffer(b
+ +(msg.split(/\r?\n+/).join(eol+b))
+ + eol))
+ })
+ fstr.end()
+ fstr.on("close", cb)
+}