monaco editor - "[ts] Unterminated regular expression literal" - javascript

TS compiler does not recognise jsx tags, and fails parsing them.
This only happens when I set the language to be 'typescript'
(and there is no built in language for 'typescriptReact' :(
How to configure monaco so it will accept jsx?
I tried:
monaco.languages.typescript.typescriptDefaults.setCompilerOptions(options)
I went through all of the options but none seem to work. (especially the jsx: 'react' option.
monaco.languages.typescript.typescriptDefaults.setDiagnosticsOptions({})
{ noSyntaxValidation: true})
works, but removes all validations from TS. :S
finally I made sure that the language is set to 'typescript':
monaco.editor.createModel("const a = <div></div>", "typescript", undefined)
(yes, I also tried the filepath)

tl;dr - yes, the file needs to be '.tsx'.
I had a single instance of Editor Model, with undefined filename.
The correct way to set filename is using Uri.file(filepath) as path,
and these errors are gone for .tsx (but not for .ts files).
as a bonus, I get to keep undo history, as long as I reuse existing models.
so yay!

Related

In VS Code Can I Validate my Javascript But Ignore a Specific Typescript Error?

I am writing Javascript in Visual Studio Code (not Typescript). However, I added "checkJs": true ("Enable type checking on JavaScript files") to my compilerOptions in jsconfig.json to enable automatic imports.
Now that I have done that, I'm getting Typescript errors (squiggly lines), for instance:
JSX element type 'Foo' does not have any construct or call signatures. ts(2604)
I could remove these by disabling validity checking, but then I'd lose normal Javascript validity checking.
My question is: is it possible to have automatic imports, and Javascript validity checking, but not have Typescript errors in VS Code? For instance, is there some flag I can set in jsconfig.json to disable errors with "ts" at the end?
And if not, how do I fix Typescript errors in a Javascript file ... without having to adopt Typescript?
EDIT: Just to help clarify the kind of solution I'm imagining ... let's say we were talking about ESLint here. Yes I could add a comment at the top of a file to make ESLint ignore that file, but then I lose all linting whatsoever.
I'm more looking for the equivalent of being able to say "ts2604": false or "ts*": false in an .eslintrc file, or something more like that. In other words, I don't want to adopt Typescript, or lose all type awareness either ... I just want VS Code's great Javascript features, without large chunks of my code being underlined by error/warning messages that I can't do anything about.
This could be a red herring, but are all your errors JSX related? TypeScript can handle JSX (in *.tsx ot *.jsx files) if you specify the factory to use for the JSX. The error looks like TS can't find the factory class (so it's got <Foo> and doesn't know what to pass it to). Typically this will be something like (the settings say React, but they're the same for Preact or other JSX libraries):
"compilerOptions": {
"jsx": "react",
"jsxFactory": "probably the same as transform-react-jsx setting in your plugins"
}
There's much more on that in the TS docs.
Generally I find it best practice to fix TS errors before JS anyway, but that isn't always practical, so another option is adding // #ts-ignore on the preceding line or // #ts-nocheck to skip type checking in the file.
// #ts-ignore is really intended for this kind of situation, but it's not a long term fix - you're upgrading, you know it works, you just need TS to skip the failing check for now. But, when you know the code works and TS is missing a definition somewhere it can be the right patch.
VS Code's JavaScript type checking is powered by TypeScript. The errors you are seeing in your JS files are not TypeScript language errors, they are the TypeScript engine saying: "Hey this JavaScript code looks like it is invalid". The TypeScript engine tries to understand JavaScript as well as possible, but JavaScript's dynamic nature can sometimes trip it up and you may need to help it along with some JSDoc annotations .
So ideally you should address these errors. If this is not possible, you can suppress the errors using a // #ts-ignore comment on the line above the error (this is offered as a quick fix for the error)
This TypeScript feature request also tracks the ability to suppress specific error codes.
Lately I have been coding in React with Visual Studio Code and we have a team recommandation for using ESLint extension.
It has many configuration capabilities, and the following one may match with your needs :
eslint.probe = an array for language identifiers for which the ESLint extension should be activated and should try to validate the file. If validation fails for probed languages the extension says silent. Defaults to ["javascript", "javascriptreact", "typescript", "typescriptreact", "html", "vue"].

SlateJS: slate-core Editor not updating value for simulated onKeyDown events

I'm attempting to simulate onKeyDown events on the Editor from slate-core -- as opposed to slate-react -- to test some plugins I am developing. However, the Editor is not updating its Value whatsoever.
I've extensively looked through the SlateJS 0.47.x documentation and from what I can tell the Editor component should respond to onKeyDown events out-of-the-box.
Here is a small codesandbox example that reproduces my problem.
^ Notice that despite me trying to simulate numerous onKeyDown events -- in the file core-editor-is-not-responding-to-on-key-down-events.js -- the value of the Editor never updates; it remains a blank document.
I am concerned about this difference in the behavior because seems like I would need to re-write functionality of inserting text as it gets typed out when said functionality I believe already exists.
Any help would be incredibly appreciated!
So it turns out to be a bug in Slate-Core, as #devinm mentioned. Without Slate-React, it doesn't react properly to onKeyDown.
I don't know how to bundle this up for other people to use, and also this issue affects a number of Slate versions so I think the best thing really is to explain what needs to be done anyway.
Note that your environment will need to support ES6 imports.
Go to the Slate codebase for the version you're using which is affected (0.44.x to 0.47.x) and find the slate-react/plugins/DOMPlugin files
Copy the contents of the directory into a new folder in your project called slate-react-dom-plugin
Copy these directories into the path alongside the slate-react-dom-plugin/index.js file - utils and constants (again, from slate-react)
Update the import paths for each module to match their new structure (note that you don't actually need every file in the utils folder, only the ones referenced by the DOMPlugin but it's just easier to copy the entire folder)
In your test use import DOMPlugin from './slate-react-dom-plugin'
When creating your test-editor, use the following plugin configuration:
new Editor({
value: value
plugins: [DOMPlugin({ plugins: [...ANY_OTHER_PLUGINS] })], // Wrap any plugins you use with the DOMPlugin
});
Run your test, and it should fire onKeyDown events as expected now
Let me know if you have any questions!

How do I apply new documentation to legacy minified file?

I'm trying to apply new documentation to legacy code that is
Undocumented
Minified (We don't have the source code)
Included in the rest of the code via window.thing = thing in the minified file, instead of using modules and exports.
Used literally everywhere. It's the base framework for the entire web application.
My main intent is to get vsCode to display some intellisense for this module when I create a new page/file, rather than having to copy&paste code from other pages/files before it will tell me how to use the module's methods. And even then, it doesn't tell me how it works. Although after a few months I can now write this code somewhat reliably without looking, I've had to unravel the minified file some to find all the methods and properties available. I should be copy&pasting imports, not the whole damn file. We're also bringing in new developers soon, and (although coworkers disagree), I want to have something more for them to look at then just 'follow the pattern on the other pages'.
We are using webpack and have the ability to use modules. I prefer the module pattern, but it is clear that those who came before us did not. Using window.thing to use the module between files. My coworkers prefer to 'follow the pattern already there', rather than trying to fix old code. I don't whole-heartedly disagree, but still. So I need to make this as unobtrusive as possible.
webapp/documentation/main.js
import './thing.js';
/**#type {thing}**/
var thing; // This does not work. `thing` is marked as any.
// So I changed the type to thingModule.
/**#type {thingModule}**/
var thing; // This works.
/**#type {thingModule}*/
window.thing; // This does not work.
/**#type {thingModule}**/
var thing = window.thing; // Works for thing
// But does not change window.thing
However, none of those above propagate into the next file.
webapp/view/someFile.js
import '../../documentation/main.js';
/**#type {thingModule}**/ var thing = window.thing;
// Cannot change below this line //
thing.addView(/*blah blah blah*/);
thing.doStuff();
This allows me to look up properties of thing. But it does change the code slightly. Not much, but just enough that it would be frowned upon if left in the code when committed. Plus, if I find other modules that need similar documentation, I don't want a growing import statement for just documentation.
I need to be able to include it in a single line that only provides documentation.
import '../../documentation/main.js';
// Cannot change below this line //
thing.addView(/*blah blah blah*/);
thing.doStuff();
In this case, thing is shown as ':any' instead of ':thingModule' like it needs to be.
tl;dr:
I need to assign the #typedef to window.thing and make the jsDoc definition propagate anywhere documentation is imported. And I need to not change the actual declaration of window.thing.

What could cause errors in combined javascript that runs fine when loaded separately?

I've written a server-side utility that is meant to manage javascript page dependencies. During development, it serves the javascript as separate files (embeds individual script tags in the order defined), and in production mode it reads the files, minifies them (Google Closure in Whitespace only mode), and embeds them via a single script tag.
For the moment, I've turned off minification to eliminate that variable...so all it is doing is joining the files together with a newline between each.
When I go to production mode, I get spurious problems in a number of the files that are embedded.
So, does anyone have any ideas of what problems I could be causing by serving a set of files as a single, concatenated file? I'm at a loss.
For those wanting more detail:
I am certain the order is correct.
The list of files in question is rather large for this example, but include jquery, angular, controllers, jquery dnd fileupload, controllers, etc.
I get "Uncaught Type Error: undefined is not a function" at this line of the combo:
(function(b){b.support.touch="ontouchend" in document;if(!b.support.touch){return;}var c=b.ui.mouse.prototype,e=c._mouseInit,a;function d(g,h){if(g.originalEvent.touches.length>1){return;}g.preventDefault();var i=g.originalEvent.changedTouches[0],f=document.createEvent("MouseEvents");f.initMouseEvent(h,true,true,window,1,i.screenX,i.screenY,i.clientX,i.clientY,false,false,false,false,0,null);g.target.dispatchEvent(f);}c._touchStart=function(g){var f=this;if(a||!f._mouseCapture(g.originalEvent.changedTouches[0])){return;}a=true;f._touchMoved=false;d(g,"mouseover");d(g,"mousemove");d(g,"mousedown");};c._touchMove=function(f){if(!a){return;}this._touchMoved=true;d(f,"mousemove");};c._touchEnd=function(f){if(!a){return;}d(f,"mouseup");d(f,"mouseout");if(!this._touchMoved){d(f,"click");}a=false;};c._mouseInit=function(){var f=this;f.element.bind("touchstart",b.proxy(f,"_touchStart")).bind("touchmove",b.proxy(f,"_touchMove")).bind("touchend",b.proxy(f,"_touchEnd"));e.call(f);};})(jQuery);
which follows some other file embeds that generate global vars:
var FocusElementDirective = function() {
...
}
var DirectiveApplier = function(){
...
}
var AgeCalculator = function(){
...
}
Another one: when I trigger an "add" event in the angular plugin for jquery fileupload, it gives Uncaught TypeError: Object # has no method 'scope'. The line it is pointing to is within the jquery fileupload angular module (line 89 of version 9.0.5):
add: function (e, data) {
if (e.isDefaultPrevented()) {
return false;
}
var scope = data.scope(), // this line
Just happening upon this and the first thing that comes to mind is that it could be something to do with global variables, one of those things Crockford complains about as a weakness of javascript.
For a quick description:
JavaScript global variables & self-invoking anonymous functions
Just off the top of my head.
So, I found it, and it turned out to be something ultra-simple...so simple that I pulled my hair out for hours looking for something technical:
I had a duplicate.
When loaded as tags, the browser only bothered to load the file once. When concatenated, the code was actually duplicated. This led to all sorts of weirdness (e.g. event handlers were getting hooked to the wrong version of things).
Coming from a compiled language background, I kinda would expect some duplicate symbol kinds of notifications...ah dynamic languages.

TypeScript use typescript-require shared files

I use TypeScript to code my javascript file with Object Oriented Programing.
I want to use the node module https://npmjs.org/package/typescript-require to require my .ts files from other files.
I want to share my files in both server and client side. (Browser) And that's very important. Note that the folder /shared/ doesn't mean shared between client and server but between Game server and Web server. I use pomelo.js as framework, that's why.
For the moment I'm not using (successfully) the typescript-require library.
I do like that:
shared/lib/message.js
var Message = require('./../classes/Message');
module.exports = {
getNewInstance: function(message, data, status){
console.log(requireTs);// Global typescript-require instance
console.log(Message);
return new Message(message, data, status);
}
};
This file need the Message.js to create new instances.
shared/classes/Message.ts
class Message{
// Big stuff
}
try{
module.exports = Message;
}catch(e){}
At the end of the fil I add this try/catch to add the class to the module.exports if it exists. (It works, but it's not really a good way to do it, I would like to do better)
If I load the file from the browser, the module.export won't exists.
So, what I did above is working. Now if I try to use the typescript-require module, I'll change some things:
shared/lib/message.js
var Message = requireTs('./../classes/Message.ts');
I use requireTs instead of require, it's a global var. I precise I'm using .ts file.
shared/classes/Message.ts
export class Message{
// Big stuff
}
// remove the compatibility script at the end
Now, if I try like this and if I take a look to the console server, I get requireTs is object and Message is undefined in shared/lib/message.js.
I get the same if I don't use the export keyword in Message.ts. Even if I use my little script at the end I get always an error.
But there is more, I have another class name ValidatorMessage.ts which extends Message.ts, it's not working if I use the export keyword...
Did I did something wrong? I tried several other things but nothing is working, looks like the typescript-require is not able to require .ts files.
Thank you for your help.
Looking at the typescript-require library, I see it hasn't been updated for 9 months. As it includes the lib.d.ts typing central to TypeScript (and the node.d.ts typing), and as these have progressed greatly in the past 9 months (along with needed changes due to language updates), it's probably not compatible with the latest TypeScript releases (just my assumption, I may be wrong).
Sharing modules between Node and the browser is not easy with TypeScript, as they both use very different module systems (CommonJS in Node, and typically something like RequireJS in the browser). TypeScript emits code for one or the other, depending on the --module switch given. (Note: There is a Universal Module Definition (UMD) pattern some folks use, but TypeScript doesn't support this directly).
What goals exactly are you trying to achieve, and I may be able to offer some guidance.
I am doing the same and keep having issues whichever way I try to do things... The main problems for me are:
I write my typescript as namespaces and components, so there is no export module with multiple file compilation you have to do a hack to add some _exporter.ts at the end to add the export for your library-output.js to be importable as a module, this would require something like:
module.exports.MyRootNamespace = MyRootNamespace
If you do the above it works, however then you get the issue of when you need to reference classes from other modules (such as MyRootNamespace1.SomeClass being referenced by MyRootNamespace2.SomeOtherClass) you can reference it but then it will compile it into your library-output2.js file so you end up having duplicates of classes if you are trying to re-use typescript across multiple compiled targets (like how you would have 1 solution in VS and multiple projects which have their own dll outputs)
Assuming you are not happy with hacking the exports and/or duplicating your references then you can just import them into the global scope, which is a hack but works... however then when you decide you want to test your code (using whatever nodejs testing framework) you will need to mock out certain things, and as the dependencies for your components may not be included via a require() call (and your module may depend upon node_modules which are not really usable with global scope hacking) and this then makes it difficult to satisfy dependencies and mock certain ones, its like an all or nothing sort of approach.
Finally you can try to mitigate all these problems by using a typescript framework such as appex which allows you to run your typescript directly rather than the compile into js first, and while it seems very good up front it is VERY hard to debug compilation errors, this is currently my preferred way but I have an issue where my typescript compiles fine via tsc, but just blows up with a max stack size exception on appex, and I am at the mercy of the project maintainer to fix this (I was not able to find the underlying issue). There are also not many of these sort of projects out there however they make the issue of compiling at module level/file level etc a moot point.
Ultimately I have had nothing but problems trying to wrestle with Typescript to get it to work in a way which is maintainable and testable. I also am trying to re-use some of the typescript components on the clientside however if you go down the npm hack route to get your modules included you then have to make sure your client side uses a require compatible resource/package loader. As much as I would love to just use typescript on my client and my server projects, it just does not seem to want to work in a nice way.
Solution here:
Inheritance TypeScript with exported class and modules
Finally I don't use require-typescript but typescript.api instead, it works well. (You have to load lib.d.ts if you use it, else you'll get some errors on the console.
I don't have a solution to have the script on the browser yet. (Because of export keyword I have some errors client side) I think add a exports global var to avoid errors like this.
Thank you for your help Bill.

Categories