How to configure Create-react-app less module with customize-cra(2.x)? - less

I used create-react-app(typescripts) to build a project, and added antd#3.26.13 with customize-cra as the website I was following told me.
I would like use the module.css, and I want to use module.less, like css, but encountered some error messages:
./src/layout/basic.module.less (./node_modules/css-loader/dist/cjs.js??ref--6-oneOf-8-1!./node_modules/postcss-loader/src??postcss!./node_modules/less-loader/dist/cjs.js??ref--6-oneOf-8-3!./src/layout/basic.module.less)
ValidationError: Invalid options object. CSS Loader has been initialized using an options object that does not match the API schema.
- options has an unknown property 'localIdentName'. These properties are valid:
object { url?, import?, modules?, sourceMap?, importLoaders?, localsConvention?, onlyLocals?, esModule? }
My code follows:
const {
override,
addWebpackAlias,
fixBabelImports,
addLessLoader,
addDecoratorsLegacy
} = require('customize-cra');
module.exports = override(
addWebpackAlias({
"#":require('path').resolve(__dirname,"src")
}),
fixBabelImports('import',{
libraryName:'antd',
libraryDirectory:'es',
style:true
}),
addLessLoader({
javascriptEnabled:true,
modifyVars:{'#primary-color':'#1DA57A'},
}),
addDecoratorsLegacy()
);

The current version of customize-cra isn't compatible with the latest version of create-react-app, to be precise with css-loader. Try to install customize-cra#next to get alpha version. They fixed that issue there.

Related

Vuelayers vl-style-icon syntax

I've been looking through the vuelayers documentation and have found little info on to use the vl-style-icon module, which is quite important if you want to create icons on your vuelayer map.
I'm pretty sure I have proper syntax when it comes to using it but marker.png won't load in through it. I've tried accessing it as just a normal image and it works fine so it is to my assumption that it's something with my syntax.
Here is my code:
<template>
<vl-map :load-tiles-while-animating="true" :load-tiles-while-interacting="true" style="height: 400px">
<vl-view :zoom.sync="zoom" :center.sync="center" :rotation.sync="rotation" projection="EPSG:4326"></vl-view>
<vl-feature v-for="crime in crimePoints" :key="crime.id">
<vl-geom-point :coordinates="crime.coords"></vl-geom-point>
<vl-style-box>
<vl-style-icon src="./marker.png" :scale="0.4" :anchor="[0.5, 1]"></vl-style-icon>
</vl-style-box>
</vl-feature>
<vl-layer-tile>
<vl-source-osm></vl-source-osm>
</vl-layer-tile>
</vl-map>
</template>
vl-style-box and vl-style-icon are the main points here. I have also checked to see if the points come up without vl-style-box and they do. What could be wrong with my code?
You can try like this:
<vl-style-icon :src="require('./marker.png')" :scale="0.4" :anchor="[0.5, 1]"></vl-style-icon>
</vl-style-box>
If you used Vue CLI to create your vue project include this in your vue.config.js file. First section tells webpack to parse url attribute on custom tags other than what is already configured (Source).
module.exports = {
chainWebpack: config => {
config.module.rule('vue').use('vue-loader').tap(options => {
options.transformAssetUrls = {
'vl-style-icon': 'src',
...options.transformAssetUrls,
};
return options;
});
}
}
Run the following command to verify the correct vue-loader configuration is there
Source
vue inspect > output.js

Vue CLI 3 Nightwatch page object configuration

I'm using Vue CLI 3 version 3.0.5.
In project configuration, I use Nightwatch as e2e test tool.
I try to use page objects, so I had nightwatch.config.js file in project root, and add page_objects_path inside like below:
{
page_objects_path : "/tests/e2e/page-objects"
}
Then I create page-objects folder as this path: /tests/e2e/page-objects.
Then I setup a page object Entry.js under that folder and try to use it in test:
/tests/e2e/page-objects/Entry.js
vmodule.exports = {
'Test Page Object': browser => {
browser
.url(process.env.VUE_DEV_SERVER_URL)
.waitForElementVisible('#app', 5000)
browser.page.Entry().sayHello()
browser.end()
}
}
And the error message shows:
Cannot read property 'Entry' of undefined .
It looks like my page object setup is not correct...
Could anyone help providing a correct implementation of NightWatch page object in Vue CLI v3.0.5 ? Thanks...
Ah, I know why it won't work.
Because nightwatch.config.js is a javascript file, I should export it first, then the plugin can read it.
module.export = {
page_objects_path : "/tests/e2e/page-objects"
}
Sorry for the dumb question.

Keystonejs 4.0 File system storage adapter image preview

How do I get an image preview for a Types.File field in the admin UI.
It says "The FS adapter supports all the default Keystone file schema fields. It also additionally supports and enables the filename path (required)." However when I try (doc):
format: function(item, file){
return '<img src="/files/'+file.filename+'" style="max-width: 300px">'
}
Nothing appears in the UI
The format function hasn't been working for a while as far as I can tell from the Keystone GitHub. I don't know if the function exists in Keystone 4.0. Reference here.
You could fork the current beta and patch the function yourself if you need this immediately.
You can find it at https://github.com/keystonejs/keystone/blob/v4.0.0-beta.5/fields/types/file/FileType.js#L81
Doesn't seem right to me, though. I hope they will fix it before releasing 4.0, along with the missing File Array type.
Image previews are now possible in the latest master branch of keystone (see https://github.com/keystonejs/keystone/pull/4509). At the moment you need to depend on the git version of keystone, so put this in your package.json and run npm install:
"keystone": "https://github.com/keystonejs/keystone.git"
In your model, specify thumb: true on the image field in question. You also need the url property in the schema. For example:
const storage = new keystone.Storage({
adapter: keystone.Storage.Adapters.FS,
fs: {
path: keystone.expandPath('./uploads/images'),
publicPath: '/images/'
},
schema: {
url: true,
}
})
ImageUpload.add({
name: { type: Types.Key, index: true },
image: {
type: Types.File,
storage: myStorage,
thumb: true
},
createdTimeStamp: { type: String }
});
The admin UI should now show a small preview of the image and a link to it.

TypeScript 2 TSX preserve and noimplicitany error TS2602: the global type 'JSX.Element' does not exist

I'm using TypeScript 2 and TSX with the preserve (not React) setting and with "noImplicitAny" enabled:
"noImplicitAny": true,
"jsx": "preserve"
The problem is, I keep getting this error when trying to build a simple TSX file:
error TS2602: JSX element implicitly has type 'any' because the global type 'JSX.Element' does not exist.
Here's an example of my TSX file:
'use strict';
import m from './m';
export default {
view() {
return (
<h1>Hello Mithril!</h1>
);
}
};
I'm trying to get TSX working with a non-React stack (Mithril). Thanks in advance!
Answer to original question: (how to solve the TS2602 error)
This is quite simple, as explained here:
As the errors say: "because the global type 'JSX.Element' does not exist"
you can define those types:
declare namespace JSX {
interface Element { }
interface IntrinsicElements { div: any; }
}
I recommend getting the react-jsx.d.ts file from DefinitelyTyped
You can use this file as a source for more complete typings (you'll need definitions for every sub-element in IntrinsicElements, i.e. div, p, a, etc.)
Getting farther with TSX and Mithril:
Once you've solved the typing issues, you'll find that you're not quite there. If you use the "jsx": "preserve" setting, the HTML code will be written directly in the generated js file, without any translation. This of course can't be loaded by a web browser (because it's a javascript file, not an html file).
I think there are two ways to make it work:
First solution that comes to mind is to use "jsx":"react" and write a small wrapper that will forward the calls to mithril, like this:
class React {
public static createElement(selector: string, attributes: object, ...children: Mithril.Child[]): Mithril.Child {
return m(selector, attributes, children);
}
}
This is the solution I'm currently using because it doesn't involve additional tools.
The other solution is to keep "jsx":"preserve" and use Babel, as described in mithril documentation, to translate the jsx file (which is generated by typescript from the tsx file) to a valid js file.
In the end, I've managed to make it work, but I found the process quite messy, with typescript/npm module system getting in the way to have JSX types extend Mithril types (so that your functions can return mithril-compatible types), etc. I had to modify the mithril typings (and drop npm #types/mithril), and add a few modules of my own.
I'm interested to know if someone solved this problem in an elegant and simple way!
Due to the lack of reputation it won't let me comment on youen's answer above so I'll include this in an answer of my own.
First of all, you can include this gist at the top of your project and name it something like mithril-jsx.d.ts so that typescript will see it as a type definition and won't compile it. The linked gist simply declares JSX.element as m.Vnode<any, any> and lists every HTML element under JSX.IntrinsicElements as any. Not a huge deal but a time saver.
Second, and the reason I'm even posting this: You do not need gulp or any other tool to compile .tsx files to mithril-using .js ones. All you have to do is specify these in your tsconfig.json
{
"compilerOptions": {
//...your other stuff here
"jsx": "react",
"jsxFactory": "m"
}
}
More information about the compiler options here: http://www.typescriptlang.org/docs/handbook/compiler-options.html
I am also developing with Mithril(2.0.3) and TypeScript(3.5.3).
TS7026: JSX element implicitly has type 'any' because no interface 'JSX.IntrinsicElements' exists.
This error message can be resolved by installing #types/react.
npm install --save-dev #types/react
tsconfig.json has the following settings.
{
"compilerOptions": {
"jsx": "react",
"jsxFactory": "m"
}
}

Including dojo/dom library to Spring Roo

How is it possible to include and use the dojo/dom library in Spring roo.
This:
<script type="text/javascript">
dojo.require('dojo/dom');
dojo.ready(function remAttr(){
dojo.removeAttr('theId', 'value');
}
);
</script>
results in:
"NetworkError: 404 Introuvable - http://localhost:8131/suivitrc/resources/dojo/dom.js"
dom.js
Could not load 'dojo/dom'; last tried '../dojo/dom.js'
Can anyone please help?
I think the version of dojo in roo is currently less than 1.7. This means you can remove the following line from your code because the remoteAttr function is part of dojo.js:
dojo.require('dojo/dom');
see here: http://dojotoolkit.org/reference-guide/1.7/dojo/removeAttr.html
The namespace => to module path is retreived by replacing periods (.), in short - you need to replace the slash with a dot. Your require should be
dojo.require('dojo.dom'); // blocking call? djConfig.async must be false
Since the error is in regards to the dojo.require specified path, this means your dojo.js is found and loaded (dojo.require is not undefined) - and baseUrl is not of concern to dojo modules.
The thing is, youre using the legacy loader to pull in an AMD module, in 1.7+ the require statement has a different look to it.
// AMD loader form is
function callbackFunctionOnComplete(dojoDom) { }
require([ "dojo/dom" ], callbackFunctionOnComplete); // non-blocking
So, how dojo.require works is following, assume that the parameter we pass as string is called 'module;
dojo.require = function(module) {
var parts = module.split('.');
1 - get toplevel namespace (global)
var packageName = parts.shift(); // first part is the package name
2 - get the filename (minus .js)
var id = parts.pop(); // the last bit
3 - translate everything in between to a path (relative to packagelocation)
var mid = parts.join("/");
4 - lookup package (from toplevel) location
var fullpath = // in pseudo
foreach dojoconfig.packages
iff obj.name == packageName
set to obj.location
5 append the rest and start downloading module
fullpath += mid + id + '.js'
transport.get(..... fullpath .....)
You need to configure dojo with dojo config. I prefer the form explained here:
http://dojotoolkit.org/reference-guide/1.7/dojo/_base/config.html#explicitly-creating-a-dojoconfig-object-before-including-the-dojo-core.
And you need to tell dojo where to find its stuff. An example:
var dojoConfig =
{
baseUrl : "/yourApp/js", // defines the js folder in your webapp
tlmSiblingOfDojo: false,
async: true,
parseOnLoad:true,
packages: [
{ name: "app", location: "app"}, // where it is in the js folder
{ name: "dojo", location: "lib/dojo" }, // where it is in the js folder
{ name: "dijit", location: "lib/dijit" },
{ name: "dojox", location: "lib/dojox" }
]
};
Also the require form you are using is deprecated. See http://livedocs.dojotoolkit.org/dojo/require