【问题标题】:Forms.context is obsolete.Context is obsolete as of version 2.5,please use a local context insteadForms.context 已过时。从 2.5 版开始,上下文已过时,请改用本地上下文
【发布时间】:2018-06-21 16:11:00
【问题描述】:

我遇到了这个问题: Forms.context 已过时。从 2.5 版开始,上下文已过时,请改用本地上下文。

我正在尝试使用 Azure Active Directory 登录,代码如下。 请帮忙。

using Xamarin.Forms;
using myMobile.Service;
using Microsoft.IdentityModel.Clients.ActiveDirectory;
using System.Threading.Tasks;

[assembly: Dependency(typeof(myMobile.Droid.Authenticator))]
namespace myMobile.Droid
{
    class Authenticator: IAuthenticator 
    {
        public async Task<AuthenticationResult> Authenticate(string tenantUrl, string graphResourceUri, string ApplicationID, string returnUri)
        {
            try
            {
                var authContext = new AuthenticationContext(tenantUrl);
                if (authContext.TokenCache.ReadItems().Any())
                    authContext = new AuthenticationContext(authContext.TokenCache.ReadItems().FirstOrDefault().Authority);

  var authResult = await authContext.AcquireTokenAsync(graphResourceUri, ApplicationID, new Uri(returnUri), new PlatformParameters((Activity)Forms.Context));

                return authResult;
            }
            catch (Exception)       
            {
                return null;
            }
        }
    }
}


// err encountered on this line :(Activity)Forms.Context)

 Forms.context is obsolete.Context is obsolete as of version2.5,please use a local context instead.

var authResult = await authContext.AcquireTokenAsync(graphResourceUri, ApplicationID, new Uri(returnUri), new PlatformParameters((Activity)Forms.Context));

//--- 更新:

 //-------- Login Page:

private async void Login()
{           
     try
     {
       var data = await DependencyService.Get<IAuthenticator>()
                  .Authenticate(AzureSettings.tenanturl, AzureSettings.GraphResourceUri, AzureSettings.ApplicationID, AzureSettings.ReturnUri);

  AzureSettings.AuthenticationResult = data;

                //NavigateTopage(data);

            }
            catch (Exception)
            { }
        }
   }

//--------- in Shared Project :

//-- interface: IAuthenticator


using Microsoft.IdentityModel.Clients.ActiveDirectory;
using System.Threading.Tasks;

namespace myMobile.Service
{
    public interface IAuthenticator
    {
        Task<AuthenticationResult> Authenticate(string tenantUrl, string graphResourceUri, string ApplicationID, string returnUri);
    }
}



//-------- in Android Project: add

1) Class : Authenticator.cs

using Android.App;
using Android.Content;
using Xamarin.Forms;
using myMobile.Service;
using Microsoft.IdentityModel.Clients.ActiveDirectory;
using System.Threading.Tasks;

[assembly: Dependency(typeof(myMobile.Droid.Authenticator))]
namespace myMobile.Droid
{
    class Authenticator: IAuthenticator 
    {
        private readonly Context _context;

        public static void Init(Context context)
        {
            _context = context;  //--error 
        }


        public async Task<AuthenticationResult> Authenticate(string tenantUrl, string graphResourceUri, string ApplicationID, string returnUri)
        {
            try
            {
                var authContext = new AuthenticationContext(tenantUrl);
                if (authContext.TokenCache.ReadItems().Any())
                    authContext = new AuthenticationContext(authContext.TokenCache.ReadItems().FirstOrDefault().Authority);

var authResult = await authContext.AcquireTokenAsync(graphResourceUri, ApplicationID, new Uri(returnUri), new PlatformParameters((Activity) _context));

                return authResult;
            }
            catch (Exception)       
            {
                return null;
            }
        }
    }
}

error : 

An Object reference is required for non-static field,method or property.Authenticator._context



//------- Class: MainActivity



namespace myMobile.Droid
{
    [Activity(Label = "myMobile", Icon = "@mipmap/icon", Theme = "@style/MainTheme", MainLauncher = true, ConfigurationChanges = ConfigChanges.ScreenSize | ConfigChanges.Orientation)]
    public class MainActivity : global::Xamarin.Forms.Platform.Android.FormsAppCompatActivity
    {
        protected override void OnCreate(Bundle bundle)
        {
            TabLayoutResource = Resource.Layout.Tabbar;
            ToolbarResource = Resource.Layout.Toolbar;

               DependencyService.Get<IAuthenticator>().Init(this);  //<-- Error

            base.OnCreate(bundle);

            global::Xamarin.Forms.Forms.Init(this, bundle);
            LoadApplication(new App());
        }
    }
}

Error Message:

IUAthenticator does not contain a definition for Init and no extension method accepting
a first argument of  type IAuthenticator

【问题讨论】:

    标签: xamarin.forms azure-active-directory


    【解决方案1】:

    您现在必须实现一个自定义构造函数,该构造函数将 Context 放入一个局部变量中并使用它而不是 this,例如 new PlatformParameters((Activity)Forms.Context)

    对于自定义渲染器,您可以使用下面的解决方案。这样做:

    public MyControlRenderer : ControlRenderer
    {
        private readonly Context _context;
    
        public MyControlRenderer(Context context) : base(context)
        {
            _context = context;
        }
    }
    

    对于像您这样的依赖服务,您必须找到一种方法来提供Context。由于 Xamarin.Forms 使用单个活动,因此您可以使用某种 init 方法。

    将此添加到您的代码中:

    public class MyService : IMyService
    {
        private static Context _context;
    
        public static void Init(Context context)
        {
            _context = context;
        }
    }
    

    现在从您的MainActivity 拨打Init,之后您应该会很好。也这样做:DependencyService.Get&lt;IMyService&gt;().Init(this);

    对于因多项活动而遇到此问题的其他人,请参阅此处的文档:https://www.davidbritch.com/2017/11/xamarinforms-25-and-local-context-on.html 这就是本文的灵感来源。

    【讨论】:

    • with base(context),这将显示错误。使用这个base(),没有错误。使用哪一个?错误:对象不包含带 1 个参数的构造函数
    • 我的错,以为是自定义渲染器,查看更新后的答案
    • 我已根据您的方法更新了整个代码库。我在 Authenticator.cs 类和 MainActivity 类中遇到错误。我做得对吗?
    • 如果您遇到错误,那么可能不会。我没有在您的回答中看到更新的更改?
    • 在更新部分:我列出了 1) LoginPage 2) 接口:IAuthenticator 3) Android 项目中的类;在 a) Authenticator 类中,我使用了您的注入方法,在 b) MainActivity 中,我添加了调用 Init 的方法。 a) & b) 都有我列出的错误。我想我可能做得不对。如果我没有正确遵循您的方法,您能否纠正我的错误。谢谢
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-12-14
    • 2021-02-16
    • 2016-02-25
    • 2019-06-28
    相关资源
    最近更新 更多