ReactJS NPM module: Undefined error - reactjs

I copied a ReactJS project to a new folder, made some changes, and it's not finding the react NPM module. I stripped the app down to 1 simple file, took out all the major code. This is driving me nuts, I deleted the node_modules folder, and ran NPM install.
I'm using watchify:
watchify --debug -t reactify app3.jsx -o ./build/app-brow.js
I Restarted my Terminal console in case that was out of sync, still can't find react.
I copied the original project to another folder, and it works OK from that copy, there's something about the code/files below that I'm missing.
It shows Uncaught TypeError: undefined is not a function, here which is the JS return code in my render:
React.createElement("div", null,
"Test, TEST TEST."
)
FILES:
app.jsx
/** #jsx React.DOM */
var React = require('react');
var App = React.createClass({
render: function() {
return (
<div>
Test, TEST TEST.
</div>
);
}
});
React.renderComponent((
<App />
), document.body);
index.html
<!DOCTYPE html>
<html>
<head>
<title>Test 3</title>
</head>
<body>
HAH... If you see this there is an error, make sure JavaScript is enabled in your browser.
<script type="text/javascript" src="build/app-brow.js"></script>
</body>
</html>
package.json
{
"name": "Test3",
"dependencies": {
"react": "0.11.x",
"reactify": "0.14.0"
}
}

Reactify is compiling your JSX in the React 0.12 style, but you are using React 0.11. Either upgrade React to 0.12.x or downgrade Reactify to a version that uses react-tools 0.11.

Related

How React JS index.js file contacting index.html for id references? [duplicate]

This question already has answers here:
Where's the connection between index.html and index.js in a Create-React-App application?
(2 answers)
Closed 3 years ago.
I recently get started with react.
My index.html contains
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="shortcut icon" href="%PUBLIC_URL%/favicon.ico">
<title>React App</title>
</head>
<body>
<div id="root"></div>
</body>
</html>
and index.js contains
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';
import './index.css';
ReactDOM.render(
<App />,
document.getElementById('root')
);
My doubt is I didn't mention index.js in any script tag in index.html. But how it is referencing the root div element in index.html? I was wondering as it is working fine. Please explain me.
I had run these commands to create the app
npm install -g create-react-app
create-react-app hello-world
cd hello-world
npm start
Create-React-App has a very interesting setup.
I started digging in the package.json npm script start
"start": "react-scripts start"
That takes me to their binary react-scripts under node_modules/.bin
I'll post the relevant stuff here.
switch (script) {
case 'build':
case 'eject':
case 'start':
case 'test': {
const result = spawn.sync(
'node',
[require.resolve('../scripts/' + script)].concat(args),
{ stdio: 'inherit' }
);
So this tells me that they are looking for script inside ../scripts/ folder.
So I go to the react-scripts npm module(node_modules/react-scripts) and open up the node_modules/react-scripts/scripts/start.js file since I was doing npm start.
Now here is where I found the webpack config I was looking for.
They were specifically referring to node_modules/react-scripts/config/webpack.config.dev.js. I'll post the relevant stuff here.
entry: [
// Finally, this is your app's code:
paths.appIndexJs,
],
plugins: [
// Generates an `index.html` file with the <script> injected.
new HtmlWebpackPlugin({
inject: true,
template: paths.appHtml,
}),
So file referred by paths.appIndexJs is the entry file in the webpack config.
And they are using HtmlWebpackPlugin to load the html at the path paths.appHtml.
Final piece of the puzzle is linking this back to the files you posted.
Posting relevant stuff from paths.js
const appDirectory = fs.realpathSync(process.cwd());
const resolveApp = relativePath => path.resolve(appDirectory, relativePath);
module.exports = {
...
appHtml: resolveApp('public/index.html'),
appIndexJs: resolveApp('src/index.js'),
...
}
So inside your application directory,
appHtml is file public/index.html
appIndexJs is file src/index.js
Your two files in question.
Wow! That was quite a journey..:P
Update 1 - As of react-scripts#3.x
The react-scripts binary under node_modules/.bin has changed the logic as below. Essentially doing the same thing.
if (['build', 'eject', 'start', 'test'].includes(script)) {
const result = spawn.sync(
'node',
nodeArgs
.concat(require.resolve('../scripts/' + script))
.concat(args.slice(scriptIndex + 1)),
{ stdio: 'inherit' }
);
The webpack configs for dev & prod has been combined into one.
const configFactory = require('../config/webpack.config');
The HTMLWebpackPlugin config looks like this - This is since they have to conditionally add production config on top of this
plugins: [
// Generates an `index.html` file with the <script> injected.
new HtmlWebpackPlugin(
Object.assign(
{},
{
inject: true,
template: paths.appHtml,
},
The paths file code has some updates
module.exports = {
...
appHtml: resolveApp('public/index.html'),
appIndexJs: resolveModule(resolveApp, 'src/index'),
...
};

Angular2 - Angular-CLI installing lodash - Cannot find module

Mac OSX El capitan | angular-cli: 0.1.0 | node: 5.4.0 | os: darwin x64
I try to install a 3rd party npm module according to the angular-cli wiki: https://github.com/angular/angular-cli/wiki/3rd-party-libs but fail. I've been struggling with this for days now and would greatly appreciate any help.
Steps to get the error:
ng new lodashtest3
cd lodashtest3
npm install lodash --save
typings install lodash --ambient --save
angular-cli-build.json:
module.exports = function(defaults) {
return new Angular2App(defaults, {
vendorNpmFiles: [
...
'lodash/**/*.js'
]
});
};
ng build
(lodash gets correctly added in dist/vendor)
system-config.ts:
/** Map relative paths to URLs. */
const map: any = {
'lodash': 'vendor/lodash/lodash.js'
};
/** User packages configuration. */
const packages: any = {
'lodash': {
format: 'cjs'
}
};
(all according to spec in
https://github.com/angular/angular-cli/wiki/3rd-party-libs)
Note - I've tried all config settings I can think of here, all giving the same result.
lodashtest3.component.ts:
import * as _ from 'lodash';
ng build
Could not start watchman; falling back to NodeWatcher for file system events.
Visit http://ember-cli.com/user-guide/#watchman for more info.
Build failed.
The Broccoli Plugin: [BroccoliTypeScriptCompiler] failed with:
Error: Typescript found the following errors:
/Users/danielmattsson/git/lodashtest3/tmp/broccoli_type_script_compiler-input_base_path-g2lDIaq6.tmp/0/src/app/lodashtest3.component.ts (2, 20): Cannot find module 'lodash'.
at BroccoliTypeScriptCompiler._doIncrementalBuild (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/broccoli-typescript.js:115:19)
at BroccoliTypeScriptCompiler.build (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/broccoli-typescript.js:43:10)
at /Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/index.js:152:21
at lib$rsvp$$internal$$tryCatch (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/node_modules/rsvp/dist/rsvp.js:1036:16)
at lib$rsvp$$internal$$invokeCallback (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/node_modules/rsvp/dist/rsvp.js:1048:17)
at lib$rsvp$$internal$$publish (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/node_modules/rsvp/dist/rsvp.js:1019:11)
at lib$rsvp$asap$$flush (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/node_modules/rsvp/dist/rsvp.js:1198:9)
at nextTickCallbackWith0Args (node.js:456:9)
at process._tickCallback (node.js:385:13)
The broccoli plugin was instantiated at:
at BroccoliTypeScriptCompiler.Plugin (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/node_modules/broccoli-plugin/index.js:10:31)
at BroccoliTypeScriptCompiler.CachingWriter [as constructor] (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/broccoli-caching-writer/index.js:21:10)
at BroccoliTypeScriptCompiler (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/broccoli-typescript.js:26:49)
at Angular2App._getTsTree (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/angular2-app.js:280:18)
at Angular2App._buildTree (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/angular2-app.js:101:23)
at new Angular2App (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/lib/broccoli/angular2-app.js:42:23)
at module.exports (/Users/danielmattsson/git/lodashtest3/angular-cli-build.js:6:10)
at Class.module.exports.Task.extend.setupBroccoliBuilder (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/lib/models/builder.js:55:19)
at Class.module.exports.Task.extend.init (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/lib/models/builder.js:89:10)
at new Class (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/node_modules/core-object/core-object.js:18:12)
at Class.module.exports.Task.extend.run (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/lib/tasks/build.js:15:19)
at /Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/lib/commands/build.js:32:24
at lib$rsvp$$internal$$tryCatch (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/node_modules/rsvp/dist/rsvp.js:1036:16)
at lib$rsvp$$internal$$invokeCallback (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/node_modules/rsvp/dist/rsvp.js:1048:17)
at /Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/node_modules/rsvp/dist/rsvp.js:331:11
at lib$rsvp$asap$$flush (/Users/danielmattsson/git/lodashtest3/node_modules/angular-cli/node_modules/angular-cli/node_modules/rsvp/dist/rsvp.js:1198:9)
EDIT: more information according to comments below
dist/index.html:
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Lodashtest3</title>
<base href="/">
<link rel="icon" type="image/x-icon" href="favicon.ico">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- Service worker support is disabled by default.
Install the worker script and uncomment to enable.
Only enable service workers in production.
<script type="text/javascript">
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('/worker.js').catch(function(err) {
console.log('Error installing service worker: ', err);
});
}
</script>
-->
</head>
<body>
<lodashtest3-app>Loading...</lodashtest3-app>
<script src="vendor/es6-shim/es6-shim.js"></script>
<script src="vendor/reflect-metadata/Reflect.js"></script>
<script src="vendor/systemjs/dist/system.src.js"></script>
<script src="vendor/zone.js/dist/zone.js"></script>
<script>
System.import('system-config.js').then(function () {
System.import('main');
}).catch(console.error.bind(console));
</script>
</body>
</html>
With the stable release and current angular-cli (1.0.0-beta.15), it's simply adding the npm package plus type definitions
npm install lodash --save
npm install #types/lodash --save-dev
For early versions such as 1.0.0-beta.15, the next is necessary. It should not be required for current versions:
Add the library to the angular-cli.json to list of global scripts (add "../node_modules/lodash/lodash.js" to the list apps[0].scripts).
See https://github.com/angular/angular-cli#global-library-installation
FWIW, as of today (1.0.0-beta.26), adding the scripts entry is not necessary anymore.
Simply add the proper entries to package.json using:
npm i --save lodash
npm i --save-dev #types/lodash
Then, in your TypeScript code, use:
import * as _ from 'lodash';
The code will run just fine.
In my case, actually adding the scripts entry was causing issues.
[updated answer] After the new version of angular-cli (1.0.0-beta.15):
just add
npm install lodash --save
npm install #types/lodash --save-dev
then add the library to the angular-cli.json to list of global scripts(add "../node_modules/lodash/lodash.js" to the list apps[0].scripts).
and in your component where you want to use , try this way
declare var _:any;
#Component({
})
export class YourComponent {
ngOnInit() {
console.log(_.chunk(['a', 'b', 'c', 'd'], 2));
}
}
before : angular-cli (1.0.0-beta.15):
add this line in src/index.html
<script src="/vendor/lodash/lodash.js" type="text/javascript"></script>
and in your component where you want to use , try this way
declare var _:any;
#Component({
})
export class YourComponent {
ngOnInit() {
console.log(_.chunk(['a', 'b', 'c', 'd'], 2));
}
}
I tried straight away , it worked for me
In order to support 3rd party libraries in Angular CLI and System.js, you have to specify them manually on system.config.ts and angular-cli-build.js.
I've answered it here with example for lodash and also other dependencies.
As of 4/15/2017 with #angular/cli 1.0.0:
You need to be very specific about which versions you install otherwise the TypeScript bindings will give all sorts of failures. What I did is update my devDependencies as follows in package.json:
"#types/lodash": "ts2.0"

Using gulp-babel gives Uncaught ReferenceError: require is not defined

I am using the following gulp.js file
var gulp = require('gulp');
var babel = require('gulp-babel');
gulp.task('bundle', bundle);
function bundle () {
gulp.src('./src/*.jsx')
.pipe(babel())
.pipe(gulp.dest('./dist'));
}
gulp.task('build', ['bundle']);
Before transpile "main.jsx" content
import React from 'react';
After Transpile, "js" files generated in the dist folder, has require('')
var _react = require('react');
while requesting for the page index.html
<body>
<div id="app" ></div>
<script src="main.js"></script>
</body>
Uncaught ReferenceError: require is not defined is shown in the console.
I know there is something wrong in the build task, but i am unable to figure out.
In the browser, you can not use require API, so you need to somehow bundle your code, you have few options:
Browserify
Webpack
Rollup
These module bundlers allow you to specify an 'entry' point and then bundle all the required modules together in a single file.
Similar questions that answer this problem:
Gulp + babelify + browserify issue

electron + angular2 loading vendor lib

I created a new angular2 app using the angularCLI (just so you know my directory structure).
Running ng serve puts all my files in the dist folder and runs the hello world app in the browser with no issue.
I'm trying to run the same app in electron, but it is unable to find all the vendor files (including #angular) since it uses the file protocol in a script src:
This
<script src="vendor/es6-shim/es6-shim.js"></script>
<script src="vendor/reflect-metadata/Reflect.js"></script>
<script src="vendor/systemjs/dist/system.src.js"></script>
<script src="vendor/zone.js/dist/zone.js"></script>
produces this
file:///vendor/es6-shim/es6-shim.js Failed to load resource: net::ERR_FILE_NOT_FOUND
file:///vendor/reflect-metadata/Reflect.js Failed to load resource: net::ERR_FILE_NOT_FOUND
file:///vendor/systemjs/dist/system.src.js Failed to load resource: net::ERR_FILE_NOT_FOUND
file:///vendor/zone.js/dist/zone.js Failed to load resource: net::ERR_FILE_NOT_FOUND
How do you prepend the correct path in the file: protocol that electron uses?
My gulpfile.js:
var gulp = require('gulp'),
del = require('del'),
runSeq = require('run-sequence');
gulp.task('clean-electron', function(){
return del('dist/electron-package/**/*', {force: true});
});
gulp.task('copy:electron-manifest', function(){
return gulp.src('./package.json')
.pipe(gulp.dest('./dist/electron-package'))
});
gulp.task('copy:electron-scripts', function(){
return gulp.src('./src/electron_main.js')
.pipe(gulp.dest('./dist/electron-package'));
});
gulp.task('copy:vendor-for-electron', function() {
return gulp.src('./dist/vendor/**/*')
.pipe(gulp.dest('./dist/electron-package/vendor'))
});
gulp.task('copy:spa-for-electron', function(){
return gulp.src(["./dist/*.*", "./dist/app/**/*"])
.pipe(gulp.dest('dist/electron-package'));
});
gulp.task('electron', function(done){
return runSeq('clean-electron', ['copy:spa-for-electron', 'copy:vendor-for-electron', 'copy:electron-manifest', 'copy:electron-scripts' ], done);
});
The closest I got was doing this:
my index.html:
<script src="vendor/es6-shim/es6-shim.js"></script>
<script src="vendor/reflect-metadata/Reflect.js"></script>
<script src="vendor/systemjs/dist/system.src.js"></script>
<script src="vendor/zone.js/dist/zone.js"></script>
<script>
console.log("In my script tag:");
var systemConfigPath = 'system-config.js';
var mainPath = 'main.js';
if (window.location.protocol == "file:"){
require(__dirname + '/vendor/es6-shim/es6-shim.js');
require(__dirname + '/vendor/reflect-metadata/Reflect.js');
require(__dirname + '/vendor/systemjs/dist/system.src.js');
require(__dirname + '/vendor/zone.js/dist/zone.js');
systemConfigPath = __dirname + '/' + systemConfigPath;
mainPath = __dirname + '/' + mainPath ;
}
System.import(systemConfigPath).then(function () {
System.import(mainPath);
}).catch(console.error.bind(console));
but that still gives me issues as the vendor files reference other files inside the same directories:
Edit:
I am now trying to use webpack to build my electron app (with no success).
I also created a github repo if you would like to see the code.
From How should I configure the base href for Angular 2 when using Electron? the answer is to change you
<base href="/">
to
<base href="./">
Okay! so I am not sure it's the best answer, as it still produces some silly errors, but here we go...
My index.html now looks like this:
<body>
<electron-angular-boilerplate-app>Loading...</electron-angular-boilerplate-app>
<!--will give errors in electron... oh well-->
<script src="vendor/es6-shim/es6-shim.js"></script>
<script src="vendor/reflect-metadata/Reflect.js"></script>
<script src="vendor/systemjs/dist/system.src.js"></script>
<script src="vendor/zone.js/dist/zone.js"></script>
<script>
// if require is defined, we are on node / electron:
if (!(typeof(require) == "undefined")){
require('./vendor/es6-shim/es6-shim.js');
require("./vendor/reflect-metadata/Reflect.js");
require("./vendor/systemjs/dist/system.src.js");
require("./vendor/zone.js/dist/zone.js");
require("./system-config.js");
require("./main.js");
} else {
System.import('system-config.js').then(function () {
System.import('main');
}).catch(console.error.bind(console));
}
</script>
</body>
This allows both my angular cli application to run and my electron app to run. The <script src=... tags still produce errors in electron as it is not able to find them. I also had to remove the System.import line from electron, so hopefully that doesn't cause any issues later on.
and to run it, we just need to make sure that the app is built and run electron in the ./dist folder:
ng build && electron ./dist
Here is the branch with my working code:
https://github.com/jdell64/electronAngularBoilerplate/tree/so-37447020-answer

ngReact can't find my react component

I've been trying to get this to work for ages, but no matter what I do the directive can't find my react component.
These are the files I'm including:
<script src="bower_components/react/JSXTransformer.js"></script>
<script src="bower_components/react/react-with-addons.js"></script>
<script src="bower_components/ngReact/ngReact.min.js"></script>
<script src="node_modules/babel-core/browser.js"></script>
<script src="static/react-components.min.js" type="text/babel"></script>
<script src="static/main.min.js"></script>
Where my components are inside the react-components.min.js file, and all of my angular code is inside main.min.js.
It's stated that you (might(?)) need to use an in browser transformator for this directive to work, so I tried that using babel, but that also doesn't work.
This is my react component:
<react-component name="Chat" watch-depth="reference"></react-component>
And in the react-components.min.js file I got a component called 'Chat':
var Chat = React.createClass({
render: function() {
return <footer className="chat chat--dark">Hello John</footer>;
}
});
core.value('Chat', Chat); // My application is bound to the core module
But it doesn't find it.. What could be wrong because no one else seems to have this issue?
JSX Compilation Issue
I believe it is a compilation error. I ran your code through an online compiler (https://babeljs.io/repl/) swap your current component code out with the block below and see if it works:
"use strict";
var Chat = React.createClass({
displayName: "Chat",
render: function render() {
return React.createElement(
"footer",
{ className: "chat chat--dark" },
"Hello John"
);
}
});
core.value('Chat', Chat); // My application is bound to the core module
JSXTransformer is deprecated you should add in a build step that uses Babel.
https://facebook.github.io/react/blog/2015/06/12/deprecating-jstransform-and-react-tools.html
Check out my blog post for the breakdown on adding JSX and ES6 support.
http://blog.tylerbuchea.com/migrating-angular-project-to-react/

Resources