Skip to content

Commit 8229cf6

Browse files
committed
WIP
1 parent c9beb6c commit 8229cf6

3 files changed

Lines changed: 68 additions & 10 deletions

File tree

tests/FSharp.Compiler.Service.Tests2/FSharp.Compiler.Service.Tests2.fsproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
<Link>Common.fs</Link>
2828
</Compile>
2929
<Compile Include="TypeTests.fs" />
30+
<Compile Include="Test.fs" />
3031
<Compile Include="..\service\Program.fs">
3132
<Link>Program.fs</Link>
3233
</Compile>
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
module X
2+
let x = 3

tests/FSharp.Compiler.Service.Tests2/TypeTests.fs

Lines changed: 65 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,15 @@ open FSharp.Compiler.SyntaxTrivia
77
open NUnit.Framework
88

99
let unsupported = "unsupported"
10-
type Stuff = SynLongIdent seq
10+
type Kind =
11+
| Type
12+
| ModuleOrNamespace
13+
type Item =
14+
{
15+
Ident : LongIdent
16+
Kind : Kind
17+
}
18+
type Stuff = Item seq
1119

1220
let rec visitSynModuleDecl (decl : SynModuleDecl) : Stuff =
1321
// TODO
@@ -27,7 +35,15 @@ let rec visitSynModuleDecl (decl : SynModuleDecl) : Stuff =
2735
| SynModuleDecl.Types(synTypeDefns, range) ->
2836
visitSynTypeDefns synTypeDefns
2937
| SynModuleDecl.ModuleAbbrev(ident, longId, range) ->
30-
visitLongIdent longId
38+
// TODO Module abbrevation can break the algorithm.
39+
// We need to either give up when seeing this or handle it properly.
40+
//
41+
// Consider the following:
42+
// module A = module A1 = let x = 1
43+
// module B = A
44+
// let x = B.A1.x
45+
failwith "Module abbreviations are not currently supported"
46+
//visitLongIdent longId
3147
| SynModuleDecl.NamespaceFragment synModuleOrNamespace ->
3248
visitSynModuleOrNamespace synModuleOrNamespace
3349
| SynModuleDecl.NestedModule(synComponentInfo, isRecursive, synModuleDecls, isContinuing, range, synModuleDeclNestedModuleTrivia) ->
@@ -651,23 +667,25 @@ and visitSynOpenDeclTarget (target : SynOpenDeclTarget) : Stuff =
651667
visitType typeName
652668
| SynOpenDeclTarget.ModuleOrNamespace(synLongIdent, range) ->
653669
visitSynLongIdent synLongIdent
670+
|> Seq.map (fun s -> {s with Kind = Kind.ModuleOrNamespace})
654671

655672
and visitSynComponentInfo (info : SynComponentInfo) : Stuff =
656673
match info with
657674
| SynComponentInfo(synAttributeLists, synTyparDeclsOption, synTypeConstraints, longId, preXmlDoc, preferPostfix, synAccessOption, range) ->
658675
seq {
659676
yield! visitSynAttributeLists synAttributeLists
660677
match synTyparDeclsOption with | Some decls -> yield! visitSynTyparDecls decls | None -> ()
661-
yield! visitLongIdent longId
678+
// Don't include this as it's a module definition rather than reference
679+
// yield! visitLongIdent longId
662680
yield! visitPreXmlDoc preXmlDoc
663681
match synAccessOption with | Some access -> yield! visitSynAccess access | None -> ()
664682
}
665683

666684
and visitLongIdent (ident : LongIdent) : Stuff =
667-
[] // TODO Check - probably wrong. LongIdents *might* be used for the same purpose as SynLongIdent
685+
[{Ident = ident; Kind = Kind.Type}]
668686

669687
and visitSynLongIdent (ident : SynLongIdent) : Stuff =
670-
[ident]
688+
[{Ident = ident.LongIdent; Kind = Kind.Type}]
671689

672690
and visitSynMatchClause (x : SynMatchClause) : Stuff =
673691
match x with
@@ -727,7 +745,7 @@ and visitSynMemberSig (x : SynMemberSig) : Stuff =
727745
visitSynField synField
728746

729747
and visitExpr (expr : SynExpr) =
730-
let l = System.Collections.Generic.List<SynLongIdent>()
748+
let l = System.Collections.Generic.List<Item>()
731749
let go (items : Stuff) =
732750
l.AddRange(items)
733751

@@ -995,17 +1013,30 @@ and visitSynModuleOrNamespace (x : SynModuleOrNamespace) : Stuff =
9951013
match x with
9961014
| SynModuleOrNamespace.SynModuleOrNamespace(longId, isRecursive, synModuleOrNamespaceKind, synModuleDecls, preXmlDoc, synAttributeLists, synAccessOption, range, synModuleOrNamespaceTrivia) ->
9971015
seq {
1016+
// Don't include 'longId' as that's module definition rather than reference
9981017
yield! synModuleDecls |> Seq.collect visitSynModuleDecl
9991018
yield! visitSynAttributeLists synAttributeLists
10001019
}
10011020

10021021
and visit (input : ParsedInput) : Stuff =
10031022
match input with
1004-
| ParsedInput.SigFile _ -> failwith unsupported
1023+
| ParsedInput.SigFile _ -> failwith "Signature files are not currently supported"
10051024
| ParsedInput.ImplFile(ParsedImplFileInput(fileName, isScript, qualifiedNameOfFile, scopedPragmas, parsedHashDirectives, synModuleOrNamespaces, flags, parsedImplFileInputTrivia)) ->
10061025
synModuleOrNamespaces
10071026
|> Seq.collect visitSynModuleOrNamespace
10081027

1028+
let topModuleOrNamespace (input : ParsedInput) =
1029+
match input with
1030+
| ParsedInput.ImplFile f ->
1031+
match f.Contents with
1032+
| [] -> failwith "No modules or namespaces"
1033+
| first :: rest ->
1034+
match first with
1035+
| SynModuleOrNamespace(longId, isRecursive, synModuleOrNamespaceKind, synModuleDecls, preXmlDoc, synAttributeLists, synAccessOption, range, synModuleOrNamespaceTrivia) ->
1036+
longId
1037+
| ParsedInput.SigFile _ ->
1038+
failwith "Sig files not supported atm"
1039+
10091040
[<Test>]
10101041
let ``Single SynEnumCase contains range of constant`` () =
10111042
let parseResults =
@@ -1048,15 +1079,39 @@ open A4
10481079
let e = A1.a
10491080
open A1
10501081
let f = a
1051-
1052-
module X = B
10531082
"""
10541083

1055-
printfn $"%+A{parseResults}"
10561084
let stuff = visit parseResults
1085+
let top = topModuleOrNamespace parseResults
1086+
printfn $"%+A{top}"
10571087
printfn $"%+A{stuff}"
10581088
()
10591089

1090+
let depends ()
1091+
1092+
[<Test>]
1093+
let ``Test two`` () =
1094+
1095+
let A =
1096+
"""
1097+
module A
1098+
open B
1099+
let x = B.x
1100+
"""
1101+
let B =
1102+
"""
1103+
module B
1104+
let x = 3
1105+
"""
1106+
1107+
let parsedA = getParseResults A
1108+
let visitedA = visit parsedA
1109+
let parsedB = getParseResults B
1110+
let topB = topModuleOrNamespace parsedB
1111+
printfn $"Top B: %+A{topB}"
1112+
printfn $"A refs: %+A{visitedA}"
1113+
()
1114+
10601115
module A1 = let a = 3
10611116
module A2 = let a = 3
10621117
module A3 = let a = 3

0 commit comments

Comments
 (0)