bdkjones / CodeKit

CodeKit 3 Issue Tracker
https://codekitapp.com
82 stars 5 forks source link

File(s) imported from a framework containing JSX won't compile #541

Open ca-miked opened 5 years ago

ca-miked commented 5 years ago

Quick, short summary: Files in a framework that contain JSX markup won't transpile. The same file living in a project will transpile properly.

Expected results: Framework files containing JSX markup will transpile.

Actual results: Framework files containing JSX markup throw errors when trying to transpile

Exact steps to reproduce: Create a new project. Add a framework with a file containing JSX markup. Import said file into your project.

A link to download a simplified project or file that shows the issue: codekit-jsx-test.zip

Your configuration (any details about your system that you think might be relevant) image

ca-miked commented 5 years ago

Hi, was curious if you had a chance to look at this yet? Please let me know if there's anything else i can supply to facilitate the process on this.

bdkjones commented 5 years ago

I grabbed the download you linked, but that appears to be just a project so I don't have a Framework to test with.

Are you just transpiling or are you also bundling the output?

bdkjones commented 5 years ago

Ah, I just connected your other email to this GitHub issue. Try this:

rename the files in the Framework from *.jsx to *.js. Does that resolve the problem? I'm looking at the Rollup configuration that CodeKit uses, and currently I only handle *.json and *.js extensions in the include-paths Rollup plugin that resolves files to Framework folders.

I'm skeptical that this is the issue, however, because it seems like the files are being FOUND correctly, they just aren't being transpiled.

ca-miked commented 5 years ago

I'll give it a try and report back. Thanks!

ca-miked commented 5 years ago

To your question above, transpiling AND bundling output.

ca-miked commented 5 years ago

Just tried renaming, getting the same transpile error. Screen Shot 2019-05-02 at 10 54 01 AM

ca-miked commented 5 years ago

I'm gonna drop an updated project that has a framework in it

ca-miked commented 5 years ago

Here's a sample project including a test framework to use. The app will import the jsx button component from the framework (once you uncomment it). Let me know what you find!

codekit-jsx-test-v2.zip

bdkjones commented 5 years ago

Can you boil the test case down to a single-file framework and a single-file project? Ideally something VERY simple—a couple lines of JSX in the framework file.

Additionally, if you can put a subfolder in the project that shows the case when all files are part of the project rather than part of the framework, that would be helpful. I'm not an expert on JSX, so the simplest possible case will help a lot.

ca-miked commented 5 years ago

Sure thing. Will get that posted up here asap. Thx

ca-miked commented 5 years ago

Here's the most simplified test case i can manage. I included a simple README on the exact steps to replicate the issue. Thanks

codekit-jsx-test-v3.zip

ca-miked commented 5 years ago

Did you have a chance to test check out the test case from May 3rd yet?

bdkjones commented 5 years ago

I have. I can reproduce the behavior, but I can't find a cause. The last thing I was looking into is whether it's possible to do this with Rollup/Babel at all. That is, those tools may not support bringing in an arbitrary file from anywhere on disk.

ca-miked commented 5 years ago

Have you checked out https://www.npmjs.com/package/rollup-plugin-includepaths ? I'm using this plugin in a custom rollup config to accomplish basically the same thing (using babel).

Thanks for digging on this.

ca-miked commented 5 years ago

I was working on a project where i had a centralized shared libs folder that I was referencing from multiple projects - this plugin made it work. This seems very similar to a framework in codekit from a lamens perspective. My 2 cents

bdkjones commented 5 years ago

I'm using that plugin in CodeKit. Can you show me your entire Rollup/Babel configuration?

ca-miked commented 5 years ago

rollup.config.js

import path from 'path';
import fs from 'fs';
import { rollup } from "rollup";
import babel from 'rollup-plugin-babel';
import resolve from 'rollup-plugin-node-resolve';
import commonjs from 'rollup-plugin-commonjs';
import includePaths from 'rollup-plugin-includepaths';

import minify from 'rollup-plugin-babel-minify';
import peerDepsExternal from 'rollup-plugin-peer-deps-external';
import sass from 'node-sass'
import postcss from 'rollup-plugin-postcss';
import copy from 'rollup-plugin-copy-glob';
import clear from 'rollup-plugin-clear';
import glob from 'glob'
import html from 'rollup-plugin-fill-html';

// PostCSS plugins
import autoprefixer from 'autoprefixer';
import cssnext from 'postcss-cssnext';
import cssnano from 'cssnano';

import livereload from 'rollup-plugin-livereload';
import browsersync from 'rollup-plugin-browsersync';

import _filter from 'lodash/filter';
import _each from 'lodash/each';
import _map from 'lodash/map';

import stringReplacer from 'rollup-plugin-string-replacer'

// compile custom cli config options
//
let _config = {};
let args = _each(
    _filter(process.argv,v => { return v.indexOf('--config-') !== -1 }), 
    v => { 
        let kv = v.replace('--config-','').split('=');
        _config[kv[0]] = kv[1];
    }
);

// `npm run build` -> `production` is true
// `npm run dev` -> `production` is false
const production = process.env.npm_lifecycle_event == 'build';

let filename = _config.id || 'main';
let basedir = 'dist'

let assetsPath =  'assets';
let jsPath = assetsPath+'/js';
let cssPath = assetsPath+'/css';
let imagesPath = assetsPath+'/images'; 
let mediaPath = assetsPath+'/media';

let inputPath = path.join(__dirname, `src/_ads/${filename}/js/main.js`);
let outputPath = path.join(__dirname, `${basedir}/${filename}/${jsPath}/main.js`);

// files to copy
//
let assetsToCopy = [
    // shared assets
    //
    { files: `src/assets/images`, dest: `${basedir}/${filename}/assets` },
    { files: `src/assets/media`, dest: `${basedir}/${filename}/assets` },

    // ad unit assets
    //
    { files: `src/_ads/${filename}/index.html`, dest: `${basedir}/${filename}` }
]

assetsToCopy = assetsToCopy.concat(_map(glob.sync(`src/_ads/${filename}/assets/images/**/*.*`, { ignore:`src/_ads/${filename}/assets/images/_*/*` }), v =>
{
    return { files:v, dest:`${basedir}/${filename}/assets/images` }
}))
assetsToCopy = assetsToCopy.concat(_map(glob.sync(`src/_ads/${filename}/assets/media/**/*.*`, { ignore:`src/_ads/${filename}/assets/media/_*/*` }), v =>
{
    return { files:v, dest:`${basedir}/${filename}/assets/media` }
}))

let includePathOptions = {
    include: {},
    paths: ['src/assets'],
    external: [],
    extensions: ['.js','.json','.jsx','.scss','.sass','.css']
};

export default 
{
    input: inputPath,
    output: 
    {
        file: outputPath,
        name: 'AD',
        format: 'iife',
        sourcemap: production ? false : 'inline',
        strict: false
    },
    watch: 
    {
        include: 'src/**',
        exclude: 'node_modules/**'
    },
    plugins: 
    [
        production && clear(
        {
            targets: [
                `${basedir}/${filename}/${assetsPath}`
            ]
        }),

        includePaths(includePathOptions),

        resolve(
        {
            jsnext: true,
            main: true,
            browser: true
        }),
        commonjs({
            include: ["node_modules/**"]
        }),
        babel(
        {
            extensions: ['.js', '.jsx'],
            exclude: 'node_modules/**',
            presets: ['@babel/env', '@babel/preset-react']
        }),

        copy(assetsToCopy, { verbose: true, watch: !production }),

        stringReplacer({
            files: `${basedir}/${filename}/index.html`,
            from: '_ENVIRONMENT_',
            to: production ? 'prod' : 'dev'
        }),

        postcss(
        {
            preprocessor: (content, id) => new Promise((resolve, reject) => {
                const result = sass.renderSync(
                { 
                    file: id,
                    includePaths: [
                        path.resolve('node_modules'),
                        path.resolve('src/assets/styles')
                    ]
                })
                resolve({ code: result.css.toString() })
            }),
            plugins: 
            [
                cssnext({ warnForDuplicates: false, }),
                autoprefixer(),
                cssnano()
            ],
            sourceMap: !production,
            minimize:   production ? { safe: true } : null,
            extract:    path.join(__dirname, `${basedir}/${filename}/${cssPath}/main.css`)
        }),

        production && minify(
        {
            comments: false,
            sourceMap: false,
            banner: '//'
        }),

        !production && livereload(`${basedir}/${filename}/${cssPath}/main.css`),
    ]
}
ca-miked commented 5 years ago

All my experience is with webpack and this was my first go at rollup, so I'm no expert... I would imagine there are better ways to go at what I'm trying to do but hopefully this helps!

ca-miked commented 5 years ago

babel.rc

{
    "presets": [
        "babel-preset-primavera",
        ["@babel/preset-env", {
            "modules": false
        }]
    ],
    "plugins": [
        "@babel/plugin-syntax-jsx",
        "@babel/plugin-syntax-dynamic-import",
        ["@babel/plugin-transform-react-jsx", { "pragma": "dom" }]
    ]
}
bdkjones commented 5 years ago

Select CodeKit in your Applications folder. Right-click and choose "View Package Contents". Search in that folder (and subfolders) for a file named rollupAPITemplate.js.

Open that file in a text editor. On line 28, add .jsx to the extensions array. Save the file. Restart CodeKit and see if that solves the problem for you.

ca-miked commented 5 years ago

Doing that now. Also, for the framework should any of the babel react config stuff be enabled? I wasn't exactly sure what should be on/off in the framework config

ca-miked commented 5 years ago

Current on the framework I have babel configured as follows:

image

bdkjones commented 5 years ago

That should be good. The answer really depends on how your project is setup and what you’re doing in it—these configurations can get just stupidly-complex.

Sent from my iPhone

On Jun 10, 2019, at 16:36, ca-miked notifications@github.com wrote:

Current on the framework I have babel configured as follows:

— You are receiving this because you commented. Reply to this email directly, view it on GitHub, or mute the thread.

ca-miked commented 5 years ago

I hear that. Will report back after running some tests. Thx

jenswittmann commented 3 years ago

Hello @bdkjones , i came across today using JSX with CodeKit. When check "Enable Support for: React" under Babel Settings and using React JS it works fine now (using Babel for Transpile and IIFE as Bundle Format). Thanks a lot!

Now i want to use https://preactjs.com or https://mithril.js.org for a new project. Transpiling works with "Enable Support for: React", but i got the following Error when open the webpage (no matter if preact or mitrhil):

ReferenceError: Can't find variable: React

Here is the code i use for preact.js:

import { h, render, Component } from "preact";

class Lunch extends Component {
    constructor() {
        super()
    }

    render() {
        let time = 'Lunch';
        return <span>{time}</span>;
    }
}

render(<Lunch />, document.body);

I also try to add a .babelrc file and add the following. But the Console Error stil exists, no error when transpilling.

{
  "plugins": [
    ["@babel/plugin-transform-react-jsx", {
      "pragma": "h",
      "pragmaFrag": "Fragment",
    }]
  ]
}

(Have a look here: https://preactjs.com/guide/v10/getting-started#setting-up-jsx)

Do you have an idea or workaround to fix this?

Edit: I found a quick workaround. Using the following plugins to turn JSX to HTM.

Install the following npm packages via Codekit:

Add this to "Babel Custom Plugin List" under Codekit Project Settings:

transform-jsx-to-htm,babel-plugin-htm

bdkjones commented 3 years ago

Don’t specify plugins in the .babelrc file. Add them to the “Custom Plugins” list in Project Settings > Babel in CodeKit. Plugins won’t be loaded from .babelrc because CodeKit overrides those with the plugins specified in the app’s UI. To avoid that, your other option is to change CodeKit to use ONLY the settings specified in babel config files. That option is in the Babel settings area as well.

On 9 Nov 2020, at 09:14, Jens Wittmann notifications@github.com wrote:

Hello @bdkjones https://github.com/bdkjones , i came across today using JSX with CodeKit. When check "Enable Support for: React" under Babel Settings and using React JS it works fine now (using Babel for Transpile and IIFE as Bundle Format). Thanks a lot!

Now i want to use https://preactjs.com https://preactjs.com/ or https://mithril.js.org https://mithril.js.org/ for a new project. Transpiling works with "Enable Support for: React", but i got the following Error when open the webpage (no matter if preact or mitrhil):

ReferenceError: Can't find variable: React Here is the code i use for preact.js:

import { h, render, Component } from "preact";

class Lunch extends Component { constructor() {}

render() {
    let time = 'Lunch';
    return <span>{time}</span>;
}

}

render(, document.body); I also try to add a .babelrc file and add the following. But the Console Error stil exists, no error when transpilling.

{ "plugins": [ ["@babel/plugin-transform-react-jsx", { "pragma": "h", "pragmaFrag": "Fragment", }] ] } (Have a look here: https://preactjs.com/guide/v10/getting-started#setting-up-jsx https://preactjs.com/guide/v10/getting-started#setting-up-jsx)

Do you have an idea or workaround to fix this?

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub https://github.com/bdkjones/CodeKit/issues/541#issuecomment-724150642, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAHCGZUOBRQARQHLA7AIJD3SPAPPFANCNFSM4HHARITA.