Skip to content

Instantly share code, notes, and snippets.

View davewasmer's full-sized avatar

Dave Wasmer davewasmer

View GitHub Profile
function copyUrlToClipboard() {
let url = getUrlThatICareAbout();
// Check the docs here, you'll need to pass in a DataTransfer object,
// so you'll need to lookup the docs for how to create one that captures
// the url string above.
// https://developer.mozilla.org/en-US/docs/Web/API/Clipboard/write
navigator.clipboard.write(/* some DataTransfer object */)
}
@davewasmer
davewasmer / config.js
Created July 20, 2019 22:37
Mirage & GraphQL
import config from '../config/environment';
import { makeExecutableSchema } from 'graphql-tools';
import { graphql } from 'graphql';
import schemaString from './schema.graphql';
// Define your Mirage resolvers (we usually do separate files, import, and merge)
const resolvers = {};
export default function() {
@davewasmer
davewasmer / denali-parallel-tests-and-unit-tests.md
Created January 18, 2018 00:59
A note describing some of the under-the-hood caveats of unit testing in Denali

tl;dr: Your Denali tests will run with normal Ava concurrency, except for unit tests. Unit tests will always be run serially, thanks to the quirks of parallel testing.

If you landed here, you might be wondering why your Denali app unit tests run serially - and there isn't even an option to allow them to run concurrently, which is the default for all other Denali tests, and for Ava in general.

The problem

Running tests concurrently means they cannot share state. For example:

let x;
@davewasmer
davewasmer / braindump.md
Last active January 17, 2018 23:36
Denali Testing in a post-bundler world

Why do the bundler in the first place? Because we want a pseudo global container reference?

Why do we need a pseudo global container reference? Because we want parallel test execution, which means multiple containers in the same process And we want clean Model APIs, like Post.getByAuthor But multiple containers in the same process means every object needs to be handed the reference to the "right" container it belongs to Which means the container needs to control instantiation of everything, which we want to avoid We want to avoid container controlling instantiation because that means ugly Model APIs (i.e. no new Post()), since we can no longer allow users to instantiate

@davewasmer
davewasmer / index.js
Created January 7, 2018 03:55
devcert test script
const devcert = require('devcert');
const https = require('https');
devcert.certificateFor('my-app.test').then((ssl) => {
https.createServer(ssl, (req, res) => {
res.write('<h1>Hello world - devcert is working</h1>');
res.end();
}).listen(3000);
});

The status quo

Right now, Denali only looks at top level dependencies for container lookups. The reason for this is twofold:

  1. We probably don't want deep dependencies show up in the container namespace - that might be surprising / unexpected
  2. More importantly, the container is a flat, shared namespace, but node modules are a dependency graph - meaning the same dependency can show up multiple times in the graph, potentially at different versions. It's not clear how that should map to a single, shared, flat namespace.

So as a result of (1) and (2), Denali today only looks to top level dependencies when doing container lookups - it won't look farther than that.

The problem

The goal

I usually find it help to start with the API we want, and work backwards. For models, we want something like:

import Post from '../models/post';

class CreatePost extends Action {
  respond({ body }) {
    let post = new Post();   // <- Just a simple `new Post()`
@davewasmer
davewasmer / controllers.application.js
Last active September 25, 2017 16:16
parent-controller-query-params
import Ember from 'ember';
export default Ember.Controller.extend({
appName: 'Ember Twiddle'
});
Node: v6.9.5
npm: 3.10.10
denali@0.0.26 /Users/daw/projects/oss/denali/denali
├── @types/accepts@1.3.2
├── @types/bluebird@3.5.3
├─┬ @types/body-parser@1.16.3
│ └─┬ @types/express@4.0.35
│ ├── @types/express-serve-static-core@4.0.40
│ └─┬ @types/serve-static@1.7.31
│ └── @types/mime@0.0.29
// foo is a class, container should create only one instance and always return that instance
container.register(foo, { singleton: true, instanstiate: true });
// foo is an instance of a class, container should always return foo exactly
container.register(foo, { singleton: true, instanstiate: false });
// foo is a class, container should always return a new instance
container.register(foo, { singleton: false, instanstiate: true });
// ??