Skip to content

Commit 6a285df

Browse files
committed
Fix new implementation of structs with protocol implementations
1 parent e1026bc commit 6a285df

File tree

6 files changed

+44
-19
lines changed

6 files changed

+44
-19
lines changed

lib/elixir_script/translator.ex

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -621,6 +621,21 @@ defmodule ElixirScript.Translator do
621621
{ js_ast, env }
622622
end
623623

624+
defp do_translate({:raise, _, [{:__aliases__, _, _} = alias_info]}, env) do
625+
module = case create_module_name(alias_info, env) do
626+
{module, _} ->
627+
module
628+
module ->
629+
module
630+
end
631+
632+
{call, _} = Call.make_module_function_call(module, :__struct__, [], env)
633+
634+
js_ast = JS.throw_statement(call)
635+
636+
{ js_ast, env }
637+
end
638+
624639
defp do_translate({:raise, _, [message]}, env) do
625640
js_ast = JS.throw_statement(
626641
JS.object_expression(

lib/elixir_script/translator/kernel/defimpl.ex

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -131,7 +131,7 @@ defmodule ElixirScript.Translator.Defimpl do
131131
module
132132
end
133133

134-
ElixirScript.Translator.translate!(module)
134+
ElixirScript.Translator.translate!(module, env)
135135
end
136136

137137
end

src/javascript/lib/core/protocol.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ class Protocol {
6161
) {
6262
return this.registry.has(thing);
6363
} else if (thing[Symbol.for('__struct__')]) {
64-
return this.registry.has(Symbol.for('__struct__'));
64+
return this.registry.has(thing[Symbol.for('__struct__')]);
6565
}
6666

6767
return this.registry.has(thing.constructor);

test/app/spec/exception.spec.js

Lines changed: 5 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -30,22 +30,10 @@ describe('Exception', () => {
3030
const User = Elixir.load(Elixir.User);
3131
const ArgumentError = Elixir.load(Elixir.ElixirScript.ArgumentError);
3232

33-
expect(User.throw_something()).to.throw(ArgumentError.__struct__());
34-
35-
let struct = User.__struct__();
36-
37-
expect(Object.getOwnPropertySymbols(struct)).to.eql([
38-
Symbol.for('__struct__'),
39-
Symbol.for('first'),
40-
Symbol.for('last'),
41-
]);
42-
43-
expect(struct[Symbol.for('__struct__')]).to.eql(Symbol.for('Elixir.User'));
44-
expect(struct[Symbol.for('first')]).to.eql(null);
45-
expect(struct[Symbol.for('last')]).to.eql(null);
46-
47-
struct = User.__struct__({ [Symbol.for('first')]: 'John' });
48-
49-
expect(struct[Symbol.for('first')]).to.eql('John');
33+
try {
34+
User.throw_something();
35+
} catch (e) {
36+
expect(e[Symbol.for('message')]).to.eql('argument error');
37+
}
5038
});
5139
});

test/app/spec/struct.spec.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,4 +21,16 @@ describe('Struct', () => {
2121

2222
expect(struct[Symbol.for('first')]).to.eql('John');
2323
});
24+
25+
it('Protocol', () => {
26+
const User = Elixir.load(Elixir.User);
27+
const StringChars = Elixir.load(Elixir.ElixirScript.String.Chars);
28+
29+
const struct = User.__struct__({
30+
[Symbol.for('first')]: 'John',
31+
[Symbol.for('last')]: 'Doe',
32+
});
33+
34+
expect(StringChars.to_string(struct)).to.eql('JohnDoe');
35+
});
2436
});

test/app/src/user.ex

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,14 @@ defmodule User do
44
def throw_something() do
55
raise ArgumentError
66
end
7+
end
8+
9+
defimpl String.Chars, for: User do
10+
def to_string(nil) do
11+
""
12+
end
13+
14+
def to_string(user) do
15+
user.first <> user.last
16+
end
717
end

0 commit comments

Comments
 (0)