2013-03-23 1 views
1

첫 번째 유형 제공자를 작성하려고하는데 누군가 내가 잘못 될 수있는 부분을 지적 할 수 있는지 궁금합니다.유형 리플렉션으로 볼 수없는 제공자

저는 프리 스탠더 샘플을 사용했습니다. 나는 매우 기본적인 것을 인스턴스화하기 위해 본질적 비트로 가려 내려고 노력했지만 분명히 무언가를 놓쳤거나 또는 아마도 네임 스페이스와 관련하여 꽤 옳지 않았다. 나는 단순히 인텔리 DataProvider에를보고있다

type tp = MyFirstTypeProvider.DataProvider<username="username",password="password",product=prodId> 

작업이 줄을 얻기 위해 노력하고있어,하지만 난 종류에 대한 참조 유형이 어셈블리에서 찾을 수 없습니다 찾을 수 없다는 구불 구불 얻고있다.

namespace MyFirstProvider 

type internal MyFirstRuntimeInfo(config: TypeProviderConfig) = 
    let runtimeAssembly = Assembly.LoadFrom(config.RuntimeAssembly) 

    member val DataContextType = runtimeAssembly.GetType("MyFirstProvider.Runtime.DataContext") 
    member this.RuntimeAssembly = runtimeAssembly 

// This type defines the type provider. When compiled to a DLL, it can be added 
// as a reference to an F# command-line compilation, script, or project. 
[<TypeProvider>] 
type public Types(config: TypeProviderConfig) as this = 
    inherit TypeProviderForNamespaces() 

    let bfRuntimeInfo = MyFirstRuntimeInfo(config) 

    let rootNamespace = "MyFirstProvider" 

    let defaultUsername = "xxxxxxxxxxx" 
    let defaultPassword = "yyyyyyyyyy" 
    let defaultProductId = -1  
    let defaultToken = "none" 

    let createDataContext = bfRuntimeInfo.DataContextType.GetMethod("_Create") 

    let createTypes(username, password, productId, rootTypeName) =      let bf = new MyFirstProvider.Requests.Queries(defaultToken) 
    let schema = new MyFirstProvider.Schema.SchemaConnection(bf) 
    let rootType = ProvidedTypeDefinition(bfRuntimeInfo.RuntimeAssembly,rootNamespace,rootTypeName,baseType=Some typeof<obj>, HideObjectMethods=true) 
    let theServiceType = ProvidedTypeDefinition("Service",baseType=Some bfRuntimeInfo.DataContextType, HideObjectMethods=true) 
    let theServiceTypesClass = ProvidedTypeDefinition("ServiceTypes",baseType=Some typeof<obj>,HideObjectMethods=true) 
    theServiceTypesClass.AddMembers [ theServiceType ]  
    rootType.AddMembers [ theServiceTypesClass ] 
    rootType.AddMembersDelayed (fun() -> 
     [ yield ProvidedMethod ("GetDataContext", [], theServiceType, IsStaticMethod=true, 
           InvokeCode = (fun _args -> Expr.Call(createDataContext, [ Expr.Value defaultUsername; Expr.Value defaultPassword; Expr.Value defaultProductId ]))) 
     ])   
    rootType 

    let MyFirstType = createTypes(defaultUsername, defaultPassword, defaultProductId, "Data") 
    let paramMyFirstType = ProvidedTypeDefinition(bfRuntimeInfo.RuntimeAssembly, rootNamespace, "DataProvider", Some(typeof<obj>), HideObjectMethods = true) 
    let usernameParam = ProvidedStaticParameter("username", typeof<string>, defaultUsername) 
    let passwordParam = ProvidedStaticParameter("password", typeof<string>, defaultPassword) 
    let productIdParam = ProvidedStaticParameter("productId", typeof<int>, defaultProductId) 

    do paramMyFirstType.DefineStaticParameters([usernameParam;passwordParam;productIdParam], fun typeName providerArgs -> 
     let username = (providerArgs.[0] :?> string) 
     let password = (providerArgs.[1] :?> string) 
     let productId = (providerArgs.[2] :?> int) 
     createTypes(username, password, productId, typeName)) 

    do 
     this.AddNamespace(rootNamespace, [MyFirstType ]) 
     this.AddNamespace(rootNamespace, [paramMyFirstType ]) 

[<assembly:TypeProviderAssembly>] 
do() 

미리 많은 정보가 필요합니다.

답변

3

을 (? 당신은 빌드 프로세스에서 "로컬 복사"로 설정을 시도 할 수 있습니다) 및 스크립트 파일에서 참조, 참조 #r "provider.dll"이 붉은 물결로 밑줄 말한다 :

The type provider 'MyFirstProvider.Types' reproted an error: The type provider constructor has thrown an exception: Object reference not set to an instance of an object.

Visual Studio의 두 번째 인스턴스를 시작하고 디버거를 다른 인스턴스에 연결 (디버그 -> 프로세스에 연결)하고 디버깅중인 인스턴스에서 스크립트 파일을 열어 이러한 오류를 디버깅 할 수 있습니다. 여기에 게시 된 샘플에서

는 null 참조 예외가이 라인에 발생이 존재하지 않는 방법에 액세스하려고

let createDataContext = bfRuntimeInfo.DataContextType.GetMethod("_Create") 

. Freebase 샘플은 상대적으로 복잡한 시작점이라고 생각합니다. (여기서는 "데이터 컨텍스트"를 표현하는 객체를 사용하고 있습니다.이 패턴을 따르고 싶을 수도 있지만, 기존 패턴을 적용하는 것보다는 처음부터 빌드하는 것이 더 쉽다고 생각합니다. 암호). 좋은 출발점은 Hello World type provider 일 것입니다. 훨씬 더 간단하며 새로운 유형, 속성 및 메소드를 생성하는 방법을 보여줍니다.

+0

thx. 나는 freebase 유형 제공자를 "인스턴스화"하는 두 가지 방법을 완전히 몰랐다. api 키를 사용하거나 사용하지 않았다. MyProvider.Data 및 MyProvider.DataProvider <[params>. 나는 내가 과부하 유형의 행동을 기대하고 있다고 생각한다. 그 페니가 떨어지면 나는 일하는 것을 얻을 수 있었다! 다시 한번 Thx –

2

공급자 유형의 간단한 예제를 찾고있는 경우 File System type provider을 살펴 보는 것이 좋습니다. 상태 및 종속성 관리가 없으므로 시작하는 것이 좋습니다.

이 dll이 찾을 수없는 이유는이 dll이 유형 공급자의 dll 위치에서 표시되어야하기 때문입니다. 예를 들어, 같은 디렉토리에 있습니다. 나는 당신의 유형 제공자를 컴파일 할 때

+0

thx 대단히 - Tomas에게 내 코멘트를보십시오 –

관련 문제