       translateIr ctx, op
   (jsCall op, (join classParams, (translateIr ctx, args)))
 
+addConstraintsFrom = (ctx, {name, type}, to) ->
+  typed = ctx.type name
+  if typed and _empty to.constraints
+    inferredType = freshInstance ctx, typed
+    sub = matchType inferredType.type, (substitute ctx.substitution, type).type
+    addConstraints to, (substitute sub, inferredType).constraints
+  else
+    to
 
 irReference = (name, type, arity) ->
   {ir: irReferenceTranslate, name, type, arity}

    # log "pattern", matched.tea, pattern.tea
    unify ctx, matched.tea.type, pattern.tea.type

  # log "pattern compiel", definedNames, pattern
  for {name, id, type} in definedNames
    deps = ctx.deferredNames()

  # For explicitly typed bindings, we need to check that the inferred type
  #   corresponds to the annotated
  currentType = substitute ctx.substitution, type
  if ctx.isActuallyTyped name
    # TODO: check class constraints
    unify ctx, currentType.type, (freshInstance ctx, ctx.type name).type
  else
