Fork me on GitHub
#cljs-dev
<
2018-06-06
>
martinklepsch10:06:04

Unusual cases but might be worth considering regardless: using str in an :advanced build adds around 90K to the build over using goog/buildString. I’m not sure these are API compatible but for people authoring JS libs in CLJS this is a high price and they are usually better of avoiding str due to this.

😱 16
martinklepsch11:06:30

Just using goog.string/buildString in str doesn’t change anything. (Tried with apply and with a wrong impl that ignores varargs.)

favila14:06:57

This was backed out but I think a more modest one was put back in much later

martinklepsch14:06:18

oh wow, that’s a huge list of comments 😄

dnolen16:06:07

@martinklepsch that’s known problem but there’s really no way around it

dnolen16:06:40

endless vistas of broken windows

dnolen16:06:51

why this isn’t stripped during minification boggles the mind

justinlee16:06:22

the reason (I think) is because (1) strict javascript and non-strict javascript have mutually exclusive semantics, (2) es6 modules are, by definition, strict, so babel adds the strict mode to the top of the file during transpile

dnolen16:06:04

I don’t buy it

dnolen16:06:27

removing it shouldn’t really matter for final concatenated thing

dnolen16:06:59

anyways, @symfrog we could add a flag to strip "use strict" from foreign deps

justinlee16:06:00

what don’t you buy? it’s absolutely possible to write strict-mode javascript that will not run correctly in non-strict mode

dnolen16:06:42

@lee.justin.m hrm that’s news to me, I haven’t followed changes to strict-mode

dnolen16:06:51

what can you write that won’t work in non-strict?

justinlee16:06:14

let me see if i can think of an example. given that nonstrict mode hoists variables and doesn’t have lexical scope in some places, i’d think that would break it.

dnolen16:06:49

right this is what I mean I don’t buy it 🙂

dnolen16:06:08

at least your statement about the direction of incompatibility

dnolen16:06:37

strict-mode will always work with sloppy mode

dnolen16:06:48

dropping the "use strict" can’t break anything that I can s ee

dnolen16:06:51

it’s only the other direction

dnolen16:06:59

applying strict to code that wasn’t written with it in mind

justinlee17:06:08

it’s crazy that I can’t find anything that says that definitively. js is so annoying sometimes

dnolen17:06:48

you won’t be able to find anything (I’m pretty sure) - I looked into this years ago and I came up empty

dnolen17:06:03

we just stripped "use strict" and moved on

dnolen17:06:12

@juhoteperi I thought you were testing with React 16 though, you never ran into @symfrog’s issues?

juhoteperi17:06:42

@dnolen No, never seen it

dnolen17:06:22

well in anycase, I suspect it can’t be safe anyhow (to not do anything about it as we are currently) - and other build tools have reacted

justinlee17:06:50

the strongest argument that it is safe to remove “use strict” is the fact that it is written as a string: it is designed to be ignored by older browsers.

juhoteperi17:06:36

Does the problem only happen with :modules? I don't use that

justinlee17:06:38

okay just to be pendantic: it is clear that you can write code that operates differently under non-strict mode by specifically catching an error strict mode is designed to catch. e.g.

try {
    bar = 345;
  } catch (e) {
    console.log("error");
  }
But the question is whether anybody could reasonably expect this behavior. I think @dnolen you’re probably right because stripping seems to be common

favila17:06:19

primitive "this" is different in strict vs non-strict

favila17:06:46

Number.prototype.thisType = function () {return typeof this;}
ƒ () {return typeof this;}
Number.prototype.thisTypeStrict = function () {'use strict'; return typeof this;}
ƒ () {'use strict'; return typeof this;}
(1).thisType()
"object"
(1).thisTypeStrict()
"number"

favila17:06:27

that's the only diff I am aware of where strict to non-strict weakening could create exceptions that wouldn't exist otherwise

symfrog18:06:42

@dnolen The Closure ModuleLoader fetches a module and passes the module's js to eval. Strict mode changes the behavior of eval with regard to variable and function definitions:

Strict mode eval code cannot instantiate variables or functions in the variable environment of the caller to eval. Instead, a new variable environment is created and that environment is used for declaration binding instantiation for the eval code
https://tc39.github.io/ecma262

dnolen18:06:03

none of these things matter 🙂

dnolen18:06:38

all we care about are cases where strict code won’t work in non-strict

dnolen18:06:49

I think you’ll be hard pressed to find anything realistic

symfrog18:06:41

@dnolen It matters because a global "use strict" directive applies also to the js generated from the definitions in the ClojureScript namespaces in the module. Since strict mode modifies the behavior of eval the ClojureScript definitions are also not available to the module that triggered the load of the target module, making it impossible to resolve a definition in the target module and leading to my error Uncaught TypeError: Cannot read property '$cljs$core$IFn$_invoke$arity$0$' of null when attempting to invoke the target function.

dnolen18:06:58

That’s not incompatible with what I said

dnolen18:06:49

Resolution is to strip strict and being to disable that default with a flag

bhauman20:06:43

hmmm, when a directory is supplied to cljs.build.api/inputs is as empty directory it fails with a Could not write JavaScript nil error message.

bhauman20:06:47

or rather when there are no source files found in the dir

dnolen20:06:29

probably something we just don’t account for

dnolen20:06:52

this one is pretty trivial