Skip to content

Commit b390239

Browse files
committed
#1301 Add InternalProxy attribute
1 parent b186ee2 commit b390239

File tree

5 files changed

+43
-13
lines changed

5 files changed

+43
-13
lines changed

src/compiler/WebSharper.Compiler.CSharp/ProjectReader.fs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1367,7 +1367,7 @@ let transformAssembly (comp : Compilation) (config: WsConfig) (rcomp: CSharpComp
13671367
// register all proxies for signature redirection
13681368
for TypeWithAnnotation(_, def, annot) in allTypes do
13691369
match annot.ProxyOf with
1370-
| Some p -> comp.AddProxy(def, p)
1370+
| Some p -> comp.AddProxy(def, p, annot.IsProxyInteral)
13711371
| _ -> ()
13721372

13731373
for TypeWithAnnotation(t, d, a) in allTypes do

src/compiler/WebSharper.Compiler.FSharp/ProjectReader.fs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1346,7 +1346,7 @@ let transformAssembly (logger: LoggerBase) (comp : Compilation) assemblyName (co
13461346
// register all proxies for signature redirection
13471347
for (def, annot) in classAnnotations.Values do
13481348
match annot.ProxyOf with
1349-
| Some p -> comp.AddProxy(def, p)
1349+
| Some p -> comp.AddProxy(def, p, annot.IsProxyInteral)
13501350
| _ -> ()
13511351

13521352
for t in topLevelTypes do

src/compiler/WebSharper.Compiler/AttributeReader.fs

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ module M = WebSharper.Core.Metadata
3232
[<RequireQualifiedAccess>]
3333
type private Attribute =
3434
| Macro of TypeDefinition * option<obj>
35-
| Proxy of TypeDefinition * TypeDefinition[]
35+
| Proxy of TypeDefinition * TypeDefinition[] * bool
3636
| Inline of option<string> * dollarVars: string[]
3737
| Direct of string * dollarVars: string[]
3838
| Pure
@@ -62,6 +62,7 @@ type TypeAnnotation =
6262
{
6363
ProxyOf : option<TypeDefinition>
6464
ProxyExtends : list<TypeDefinition>
65+
IsProxyInteral : bool
6566
IsJavaScript : bool
6667
IsJavaScriptExport : bool
6768
IsForcedNotJavaScript : bool
@@ -81,6 +82,7 @@ type TypeAnnotation =
8182
{
8283
ProxyOf = None
8384
ProxyExtends = []
85+
IsProxyInteral = false
8486
IsJavaScript = false
8587
IsJavaScriptExport = false
8688
IsForcedNotJavaScript = false
@@ -249,7 +251,7 @@ type AttributeReader<'A>() =
249251
| Some (:? System.Array as a) ->
250252
a |> Seq.cast<obj> |> Seq.map this.GetTypeDef |> Array.ofSeq
251253
| _ -> [||]
252-
A.Proxy (p, intfTypes)
254+
A.Proxy (p, intfTypes, false)
253255
| "InlineAttribute" ->
254256
A.Inline (this.CtorArgOption(attr), this.DollarVars(attr))
255257
| "DirectAttribute" ->
@@ -323,6 +325,7 @@ type AttributeReader<'A>() =
323325
let mutable stub = false
324326
let mutable proxy = None
325327
let mutable proxyExt = []
328+
let mutable proxyInt = false
326329
let mutable prot = None
327330
for a in attrs do
328331
match this.GetAssemblyName a with
@@ -341,9 +344,10 @@ type AttributeReader<'A>() =
341344
js <- Some true
342345
jse <- true
343346
| A.Stub -> stub <- true
344-
| A.Proxy (t, i) ->
347+
| A.Proxy (t, i, ip) ->
345348
proxy <- Some t
346349
proxyExt <- List.ofArray i
350+
proxyInt <- ip
347351
| A.Prototype p -> prot <- Some p
348352
| A.OtherAttribute -> ()
349353
| ar -> attrArr.Add ar
@@ -373,13 +377,14 @@ type AttributeReader<'A>() =
373377
jse <- true
374378
if parent.OptionalFields then
375379
if not (attrArr.Contains(A.OptionalField)) then attrArr.Add A.OptionalField
376-
attrArr |> Seq.distinct |> Seq.toArray, macros.ToArray(), name, proxy, proxyExt, isJavaScript, js = Some false, jsOpts, jse, prot, isStub, List.ofSeq reqs
380+
attrArr |> Seq.distinct |> Seq.toArray, macros.ToArray(), name, proxy, proxyExt, proxyInt, isJavaScript, js = Some false, jsOpts, jse, prot, isStub, List.ofSeq reqs
377381

378382
member this.GetTypeAnnot (parent: TypeAnnotation, attrs: seq<'A>) =
379-
let attrArr, macros, name, proxyOf, proxyExt, isJavaScript, isForcedNotJavaScript, _, isJavaScriptExport, prot, isStub, reqs = this.GetAttrs (parent, attrs)
383+
let attrArr, macros, name, proxyOf, proxyExt, proxyInt, isJavaScript, isForcedNotJavaScript, _, isJavaScriptExport, prot, isStub, reqs = this.GetAttrs (parent, attrs)
380384
{
381385
ProxyOf = proxyOf
382386
ProxyExtends = proxyExt
387+
IsProxyInteral = proxyInt
383388
IsJavaScript = isJavaScript
384389
IsJavaScriptExport = isJavaScriptExport
385390
IsForcedNotJavaScript = isForcedNotJavaScript
@@ -402,7 +407,7 @@ type AttributeReader<'A>() =
402407
}
403408

404409
member this.GetMemberAnnot (parent: TypeAnnotation, attrs: seq<'A>) =
405-
let attrArr, macros, name, _, _, isJavaScript, _, jsOptions, isJavaScriptExport, _, isStub, reqs = this.GetAttrs (parent, attrs)
410+
let attrArr, macros, name, _, _, _, isJavaScript, _, jsOptions, isJavaScriptExport, _, isStub, reqs = this.GetAttrs (parent, attrs)
406411
let isEp = attrArr |> Array.contains A.SPAEntryPoint
407412
let isPure = attrArr |> Array.contains A.Pure
408413
let warning = attrArr |> Array.tryPick (function A.Warn w -> Some w | _ -> None)

src/compiler/WebSharper.Compiler/Compilation.fs

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ type Compilation(meta: Info, ?hasGraph) =
3939
let notResolvedInterfaces = Dictionary<TypeDefinition, NotResolvedInterface>()
4040
let notResolvedClasses = Dictionary<TypeDefinition, NotResolvedClass>()
4141
let proxies = Dictionary<TypeDefinition, TypeDefinition>()
42+
let internalProxies = HashSet<TypeDefinition>()
4243

4344
let classes = MergedDictionary meta.Classes
4445
let interfaces = MergedDictionary meta.Interfaces
@@ -384,19 +385,21 @@ type Compilation(meta: Info, ?hasGraph) =
384385
member this.ToCurrentMetadata(?ignoreErrors) =
385386
if errors.Count > 0 && not (ignoreErrors = Some true) then
386387
failwith "This compilation has errors"
388+
let withoutInternalProxies d =
389+
d |> Dict.filter (fun t _ -> not (internalProxies.Contains(t)))
387390
{
388391
SiteletDefinition = this.SiteletDefinition
389392
Dependencies = if hasGraph then graph.GetData() else GraphData.Empty
390-
Interfaces = interfaces.Current
393+
Interfaces = interfaces.Current |> withoutInternalProxies
391394
Classes =
392-
classes.Current |> Dict.map (fun c ->
395+
classes.Current |> withoutInternalProxies |> Dict.map (fun c ->
393396
match c.Methods with
394397
| :? MergedDictionary<Method, CompiledMember * Optimizations * Expression> as m ->
395398
{ c with Methods = m.Current }
396399
| _ -> c
397400
)
398401
CustomTypes =
399-
customTypes.Current |> Dict.filter (fun _ v -> v <> NotCustomType)
402+
customTypes.Current |> withoutInternalProxies |> Dict.filter (fun _ v -> v <> NotCustomType)
400403
MacroEntries = macroEntries.Current
401404
Quotations = quotations.Current
402405
ResourceHashes = Dictionary()
@@ -416,8 +419,14 @@ type Compilation(meta: Info, ?hasGraph) =
416419
ExtraBundles = this.AllExtraBundles
417420
}
418421

419-
member this.AddProxy(tProxy, tTarget) =
420-
proxies.Add(tProxy, tTarget)
422+
member this.AddProxy(tProxy, tTarget, isInternal) =
423+
// if the proxy is for internal use only, drop it with a warning if a proxy for target type already exists
424+
if isInternal && (classes.Original.ContainsKey tTarget || interfaces.Original.ContainsKey tTarget || customTypes.Original.ContainsKey tTarget) then
425+
this.AddWarning (None, SourceWarning (sprintf "Proxy for internal proxy target type '%s' already exists, ignoring the internal proxy." tTarget.Value.FullName))
426+
else
427+
proxies.Add(tProxy, tTarget)
428+
if isInternal then
429+
internalProxies.Add(tTarget) |> ignore
421430

422431
member this.ResolveProxySignature (meth: Method) =
423432
if proxies.Count = 0 then meth else

src/compiler/WebSharper.Core/Attributes.fs

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,22 @@ type ProxyAttribute private () =
169169
/// Constructs a new proxy link using a type directly and allows adding inherited interfaces.
170170
new (proxiedType: Type, interfaces: Type[]) = ProxyAttribute()
171171

172+
/// Declares a type to be a proxy for another type, identified directly or
173+
/// by using an assembly-qualified name.
174+
/// Proxy exists only for use in current project.
175+
[<Sealed; U(T.Class|||T.Interface|||T.Struct)>]
176+
type InternalProxyAttribute private () =
177+
inherit A()
178+
179+
/// Constructs a new proxy link using a type directly.
180+
new (proxiedType: Type) = InternalProxyAttribute()
181+
182+
/// Constructs a new proxy link using an assembly-qualified name.
183+
new (assemblyQualifiedName: string) = InternalProxyAttribute()
184+
185+
/// Constructs a new proxy link using a type directly and allows adding inherited interfaces.
186+
new (proxiedType: Type, interfaces: Type[]) = InternalProxyAttribute()
187+
172188
/// Marks a server-side function to be invokable remotely from the client-side.
173189
[<Sealed; U(T.Method)>]
174190
type RemoteAttribute() =

0 commit comments

Comments
 (0)