[be] Extract hooks helpers to separate file
This is a precursor to allowing the set of custom hooks (and their behavior) to be configurable.
Joe Savona committed
Feb 16, 2023 at 10:38 UTC
530231712fdb60044285c3b0eee9e665433f86d6
5 files changed
+85
-76
compiler/forget/src/HIR/Hooks.ts
new
+81
@@ -0,0 +1,81 @@
1
+/**
2
+ * Copyright (c) Facebook, Inc. and its affiliates.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+import { Effect, Place, ValueKind } from "./HIR";
9
+
10
+export const HOOKS: Map<string, Hook> = new Map([
11
+ [
12
+ "useState",
13
+ {
14
+ kind: "State",
15
+ name: "useState",
16
+ effectKind: Effect.Freeze,
17
+ valueKind: ValueKind.Frozen,
18
+ },
19
+ ],
20
+ [
21
+ "useRef",
22
+ {
23
+ kind: "Ref",
24
+ name: "useRef",
25
+ effectKind: Effect.Capture,
26
+ valueKind: ValueKind.Mutable,
27
+ },
28
+ ],
29
+ [
30
+ "useFreeze",
31
+ {
32
+ kind: "Ref",
33
+ name: "useFreeze",
34
+ effectKind: Effect.Freeze,
35
+ valueKind: ValueKind.Frozen,
36
+ },
37
+ ],
38
+ [
39
+ "useMemo",
40
+ {
41
+ kind: "Memo",
42
+ name: "useMemo",
43
+ effectKind: Effect.Freeze,
44
+ valueKind: ValueKind.Frozen,
45
+ },
46
+ ],
47
+ [
48
+ "useCallback",
49
+ {
50
+ kind: "Memo",
51
+ name: "useCallback",
52
+ effectKind: Effect.Freeze,
53
+ valueKind: ValueKind.Frozen,
54
+ },
55
+ ],
56
+]);
57
+
58
+export type HookKind = "State" | "Ref" | "Custom" | "Memo";
59
+export type Hook = {
60
+ kind: HookKind;
61
+ name: string;
62
+ effectKind: Effect;
63
+ valueKind: ValueKind;
64
+};
65
+
66
+export function parseHookCall(place: Place): Hook | null {
67
+ const name = place.identifier.name;
68
+ if (name === null || !name.match(/^_?use/)) {
69
+ return null;
70
+ }
71
+ const hook = HOOKS.get(name);
72
+ if (hook != null) {
73
+ return hook;
74
+ }
75
+ return {
76
+ kind: "Custom",
77
+ name: place.identifier.name ?? "",
78
+ effectKind: Effect.Mutate,
79
+ valueKind: ValueKind.Mutable,
80
+ };
81
+}
compiler/forget/src/Inference/InferReferenceEffects.ts
+1
-73
@@ -19,6 +19,7 @@ import {
19
Place,
20
ValueKind,
21
} from "../HIR/HIR";
22
+import { parseHookCall } from "../HIR/Hooks";
23
import {
24
printMixedHIR,
25
printPlace,
@@ -810,79 +811,6 @@ function inferBlock(env: Environment, block: BasicBlock) {
811
}
812
}
813
813
-const HOOKS: Map<string, Hook> = new Map([
814
- [
815
- "useState",
816
- {
817
- kind: "State",
818
- name: "useState",
819
- effectKind: Effect.Freeze,
820
- valueKind: ValueKind.Frozen,
821
- },
822
- ],
823
- [
824
- "useRef",
825
- {
826
- kind: "Ref",
827
- name: "useRef",
828
- effectKind: Effect.Capture,
829
- valueKind: ValueKind.Mutable,
830
- },
831
- ],
832
- [
833
- "useFreeze",
834
- {
835
- kind: "Ref",
836
- name: "useFreeze",
837
- effectKind: Effect.Freeze,
838
- valueKind: ValueKind.Frozen,
839
- },
840
- ],
841
- [
842
- "useMemo",
843
- {
844
- kind: "Memo",
845
- name: "useMemo",
846
- effectKind: Effect.Freeze,
847
- valueKind: ValueKind.Frozen,
848
- },
849
- ],
850
- [
851
- "useCallback",
852
- {
853
- kind: "Memo",
854
- name: "useCallback",
855
- effectKind: Effect.Freeze,
856
- valueKind: ValueKind.Frozen,
857
- },
858
- ],
859
-]);
860
-
861
-type HookKind = "State" | "Ref" | "Custom" | "Memo";
862
-type Hook = {
863
- kind: HookKind;
864
- name: string;
865
- effectKind: Effect;
866
- valueKind: ValueKind;
867
-};
868
-
869
-export function parseHookCall(place: Place): Hook | null {
870
- const name = place.identifier.name;
871
- if (name === null || !name.match(/^_?use/)) {
872
- return null;
873
- }
874
- const hook = HOOKS.get(name);
875
- if (hook != null) {
876
- return hook;
877
- }
878
- return {
879
- kind: "Custom",
880
- name: place.identifier.name ?? "",
881
- effectKind: Effect.Mutate,
882
- valueKind: ValueKind.Mutable,
883
- };
884
-}
885
-
814
function hasContextRefOperand(env: Environment, instrValue: InstructionValue) {
815
for (const place of eachInstructionValueOperand(instrValue)) {
816
if (env.isDefined(place) && env.kind(place) === ValueKind.Context) {
compiler/forget/src/ReactiveScopes/FlattenScopesWithHooks.ts
+1
-1
@@ -12,7 +12,7 @@ import {
12
ReactiveStatement,
13
ReactiveValue,
14
} from "../HIR";
15
-import { parseHookCall } from "../Inference/InferReferenceEffects";
15
+import { parseHookCall } from "../HIR/Hooks";
16
import {
17
ReactiveFunctionTransform,
18
Transformed,
compiler/forget/src/ReactiveScopes/InferReactiveIdentifiers.ts
+1
-1
@@ -12,7 +12,7 @@ import {
12
ReactiveFunction,
13
ReactiveInstruction,
14
} from "../HIR/HIR";
15
-import { parseHookCall } from "../Inference/InferReferenceEffects";
15
+import { parseHookCall } from "../HIR/Hooks";
16
import { assertExhaustive } from "../Utils/utils";
17
import {
18
eachReactiveValueOperand,
compiler/forget/src/TypeInference/InferTypes.ts
+1
-1
@@ -8,8 +8,8 @@ import {
8
TypeId,
9
TypeVar,
10
} from "../HIR/HIR";
11
+import { parseHookCall } from "../HIR/Hooks";
12
import { eachInstructionOperand } from "../HIR/visitors";
12
-import { parseHookCall } from "../Inference/InferReferenceEffects";
13
14
function isPrimitiveBinaryOp(op: t.BinaryExpression["operator"]) {
15
switch (op) {