aduros / wasm4

Build retro games using WebAssembly for a fantasy console.
https://wasm4.org
ISC License
1.17k stars 172 forks source link

Getting started does not work for AssemblyScript #9

Closed ttulka closed 3 years ago

ttulka commented 3 years ago

When following the Getting started tutorial I spotted several problems:

  1. Installing w4 as global is not the best solution as it may differ for projects and it is problematic to update. Better to be installed locally and executed via npx. See https://www.assemblyscript.org/quick-start.html for inspiration.
  2. Initialization doesn't work - The result from Setup instructions is Cannot GET / for http://localhost:4444/
  3. There are library files in src - wasm4.ts is a library source, I would expect it to be referenced in package.json as a devDependencies, not in the src directory as it is not supposed to be edited by the user.
aduros commented 3 years ago

About initialization not working (#2), whoops, I just fixed it and released to npm. Thanks so much for flagging that! You can update to the latest version with npm install -g wasm4.

As for your first point about w4 not being a global package, I think you're right that it makes sense from an AssemblyScript point of view. All of the other languages don't have a package.json though, so a global install would be required for them, so I decided to recommend the global install for consistency.

That said, if you prefer, you can still make wasm4 a local dependency for AssemblyScript projects by including something like this in package.json:

{
  "name": "cart",
  "version": "1.0.0",
  "scripts": {
    "build": "asc --target release",
    "build:debug": "asc --target debug",
    "start": "w4 watch"
  },
  "devDependencies": {
    "assemblyscript": "^0.19.5",
    "wasm4": "^1.0.1"
  }
}

Note the addition of the start script so that you can just run npm start to run w4 watch during development.

Lastly about the wasm4.ts API stubs living in the project source code, this decision was subjective but basically came down to 3 things:

  1. Learnability: Including this file makes it more obvious how wasm4 works. I think if it was hidden away it wouldn't be as clear how the runtime works.
  2. Parity with other languages: C would require a wasm4.h file somewhere. Rust I guess we could maintain a crate, and Go could use whatever they use to manage dependencies. But just putting the API stubs in a single file bundled with projects prevents so much unnecessary complexity.
  3. Keeping the base API slim: By design the API stubs are meant to be minimalist. It's just constants and external function declarations. I think if the API was abstracted away in a library, I would be tempted to add more complex abstractions (eg: functions that return complex objects). Users should be able to build those abstractions on top of wasm4, but I'm feeling like the base API should be dead simple.

Of course a big downside is whenever a new method is added to wasm4, projects will have to update their wasm4.ts/.h/.rs/.go to use them and that's not ideal...

What are your thoughts about all of this? Thanks a lot for your insightful feedback!

ttulka commented 3 years ago

Alright, I got that. Basically, all mentioned have a root cause in the support of multiple languages... it sounds plausible, but maybe it has more trade-offs now than necessary:

Even putting wasm4 as a project dependency does not help me with project initialization as the following does not work:

mkdir wasm4-test
cd wasm4-test
npm init -y
npm i wasm4 -D
npx w4 new --assemblyscript .

Error: EEXIST, file already exists package.json

I guess there is nothing to prevent it from working in both "global" and this way as well.

As an AS or Rust or Go or C developer, I very likely don't care about the other languages, which means the consistency you are talking about focuses only on wasm4 tooling development, not on the users.


As I can live with the global wasm4, having the library in src is for me still something very alien:

  1. Learnability - as there is no implementation a .d.ts file in node_modules/wasm4 would do the job well. My VS Code is pretty handy in showing me what I need :-)
  2. Parity with other languages - the argument from above applies here, as a user I don't really care
  3. Keeping the base API slim - I fully agree on this, but it has nothing to do with putting it into the src.

Users should be able to build those abstractions on top of wasm4

Exactly, the API should be extendable, but editable. Putting it into the source, users would tend to edit it directly, which is obviously problematic.

It would make sense if the user is seen not just as a game developer but as a platform developer as well (again "who is the user?"). I guess the main focus should be on game developers, right? At least I wouldn't mix it in one. I either develop a game or the platform, not both in the very same project. For platform development, I would expect a separate tool like w4 new-platform ... or similar.

Anyway, it is great stuff - thanks for this! :-)

aduros commented 3 years ago

You make a good point about users not caring about the other languages... Lemme think about it some more. I'm still a bit reluctant to have a different "getting started" workflow for AS because it would fragment the documentation.

ttulka commented 3 years ago

But wouldn't you need it anyway? Your doc describes only AS so far, right? https://wasm4.org/docs/getting-started/setup

aduros commented 3 years ago

The doc is AS-centric, but the only difference for using other languages is just changing --assemblyscript to --rust or whatever else.

ttulka commented 3 years ago

Is it really so? In the Setup page, there are these commands to be executed:

w4 new --assemblyscript hello-world
cd hello-world
npm install
npm run build
w4 run build/cart.wasm

I guess at least there three will differ for other languages:

w4 new --assemblyscript hello-world
npm install
npm run build

Am I missing something?

aduros commented 3 years ago

Right, the build command will be different, but it should be pretty similar. Running w4 new will print out the build and run command.

For example, for C, it's:

w4 new --c hello-world
cd hello-world
make
w4 run build/cart.wasm

Maybe this needs to be accentuated in the docs.

ttulka commented 3 years ago

Maybe this needs to be accentuated in the docs.

Agreed. I think the tab-based solution for all languages will be good.

This brings us to the situation when we do have different (yet similar) setup instructions... :-)

aduros commented 3 years ago

Agreed. I think the tab-based solution for all languages will be good.

That's a good suggestion, I went ahead and implemented it https://wasm4.org/docs/getting-started/setup/

There are also standalone download links for w4 with no nodejs/npm dependency, useful for non-AssemblyScript folks.

ttulka commented 3 years ago

I am happy with this solution.