From 0321236b1b11d0429901cc24e64366153ec07fcc Mon Sep 17 00:00:00 2001 From: Keyan Zhang Date: Sat, 4 Jun 2016 14:43:56 -0700 Subject: [PATCH] [Docs] Error Decoder Page (#6946) --- Rakefile | 9 ++- _js/ErrorDecoderComponent.js | 111 +++++++++++++++++++++++++++++++++++ docs/error-decoder.md | 13 ++++ 3 files changed, 132 insertions(+), 1 deletion(-) create mode 100644 _js/ErrorDecoderComponent.js create mode 100644 docs/error-decoder.md diff --git a/Rakefile b/Rakefile index 546f7dba..d50dc5b1 100644 --- a/Rakefile +++ b/Rakefile @@ -61,8 +61,15 @@ task :update_acknowledgements do File.open('_data/acknowledgements.yml', 'w+') { |f| f.write(cols.to_yaml) } end +desc "copy error codes to docs" +task :copy_error_codes do + codes_json = File.read('../scripts/error-codes/codes.json') + codes_js = "var errorMap = #{codes_json.chomp};\n" + File.write('js/errorMap.js', codes_js) +end + desc "build into ../../react-gh-pages" -task :release => [:update_version, :js, :fetch_remotes] do +task :release => [:update_version, :js, :fetch_remotes, :copy_error_codes] do system "jekyll build -d ../../react-gh-pages" end diff --git a/_js/ErrorDecoderComponent.js b/_js/ErrorDecoderComponent.js new file mode 100644 index 00000000..7ac94522 --- /dev/null +++ b/_js/ErrorDecoderComponent.js @@ -0,0 +1,111 @@ +/** + * Copyright (c) 2013-present, Facebook, Inc. + * All rights reserved. + * + * This source code is licensed under the BSD-style license found in the + * LICENSE file in the root directory of this source tree. An additional grant + * of patent rights can be found in the PATENTS file in the same directory. + */ +/* global React ReactDOM errorMap:true */ +'use strict'; + +function replaceArgs(msg, argList) { + let argIdx = 0; + return msg.replace(/%s/g, function() { + const arg = argList[argIdx++]; + return arg === undefined ? '[missing argument]' : arg; + }); +} + +function urlify(str) { + const urlRegex = /(https:\/\/fb\.me\/[a-z\-]+)/g; + + const segments = str.split(urlRegex); + + for (let i = 0; i < segments.length; i++) { + if (i % 2 === 1) { + segments[i] = ({segments[i]}); + } + } + + return segments; +} + +// ?invariant=123&args[]=foo&args[]=bar +function parseQueryString() { + const rawQueryString = window.location.search.substring(1); + if (!rawQueryString) { + return null; + } + + let code = ''; + let args = []; + + const queries = rawQueryString.split('&'); + for (let i = 0; i < queries.length; i++) { + const query = decodeURIComponent(queries[i]); + if (query.indexOf('invariant=') === 0) { + code = query.slice(10); + } else if (query.indexOf('args[]=') === 0) { + args.push(query.slice(7)); + } + } + + return [code, args]; +} + +function ErrorResult(props) { + const code = props.code; + const errorMsg = props.msg; + + if (!code) { + return ( +

When you encounter an error, you'll receive a link to this page for that specific error and we'll show you the full error text.

+ ); + } + + return ( +
+

The full text of the error you just encountered is:

+ {urlify(errorMsg)} +
+ ); +} + +class ErrorDecoder extends React.Component { + constructor(...args) { + super(...args); + + this.state = { + code: null, + errorMsg: '', + }; + } + + componentWillMount() { + const parseResult = parseQueryString(); + if (parseResult != null) { + const [code, args] = parseResult; + if (errorMap[code]) { + this.setState({ + code: code, + errorMsg: replaceArgs(errorMap[code], args), + }); + } + } + } + + render() { + return ( + + ); + } +} + +ReactDOM.render( + , + document.querySelector('.error-decoder-container') +); diff --git a/docs/error-decoder.md b/docs/error-decoder.md new file mode 100644 index 00000000..76d13b39 --- /dev/null +++ b/docs/error-decoder.md @@ -0,0 +1,13 @@ +--- +id: error-decoder +title: Error Decoder +permalink: error-decoder.html +--- + +In the minified production build of React, we avoid sending down full error messages in order to reduce the number of bytes sent over the wire. + +We highly recommend using the development build locally when debugging your app since it tracks additional debug info and provides helpful warnings about potential problems in your apps, but if you encounter an exception while using the production build, this page will reassemble the original text of the error. + + +
+