علامة مخصصة في صفحة لديه SPContext.الحالية التي هي دائما فارغة
-
10-12-2019 - |
سؤال
وجدت الحل
الحل هو إضافة جذر مجموعة الموقع (كما كان رمز التشغيل في الموقع الفرعي ، دون جذر الموقع).
انظر هذا الحل
تحديث مهم (على أساس ردود الفعل التي وردت حتى الآن)
لا يكون لديك Visual Studio مثبتا على SharePoint Server 2013.كل شيء يتم ترجمة التعليمات البرمجية في Visual Studio 2012 عن بعد باستخدام المراجع المطلوبة SharePoint 2013 DLLs و رقميا بحيث يمكن نشرها في ذاكرة التخزين المؤقتة للتجميع العمومي على SharePoint Server 2013.
على المستوى الأكثر أساسية هذا البيان فشل في نقطة
Page_Load()
;SPContext.Current.Site.WebApplication.GetIisSettingsWithFallback( SPContext.Current.Site.Zone );
لأن
SPContext.Current
هو دائماnull
.
الخلفية
يحتاج العميل هناك موقع SharePoint إلى يمكن الوصول إليها باستخدام النموذج على أساس مصادقة المستخدمين الخارجيين ويندوز مصادقة المستخدمين الداخليين (الشركات).مرت ويكون الإعداد المصادقة على حد سواء مقدمي الآن الحصول على تسجيل الدخول الافتراضية.
على الرغم من أن كل شيء يعمل مصادقة Windows لا يزال يعرض مزود شاشة اختيار عندما يريد العميل على مصادقة Windows فقط تمرير تلقائيا من خلال عرض نماذج التوثيق القائم على شاشة تسجيل الدخول إذا فشل ذلك.
تكافح هذه الأيام بعد النظر في العديد من المدونات و المقالات أشعر أنني لست كذلك على طول وهذا هو الاكتئاب.في هذه اللحظة لا أستطيع تجريب ما إذا أنا في عداد المفقودين شيء حقا أساسيا.
علامة مخصصة في صفحة
الصفحة يوجد مقرها خارج خليط من ؛
%CommonProgramFiles%\Microsoft Shared\Web Server Extensions\15\Template\IdentityModel\Login\default.aspx
%CommonProgramFiles%\Microsoft Shared\Web Server Extensions\15\Template\IdentityModel\Forms\default.aspx
هذا هو مجرد المحاولة الأولى و أدرك أنني لن تحتاج إلى كل هذه الضوابط في نهاية المطاف ، أردت فقط أن نرى كيف تسير الأمور شنق معا.
<%@ Assembly Name="Microsoft.SharePoint.IdentityModel, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="SharepointIdentity" Namespace="Microsoft.SharePoint.IdentityModel" Assembly="Microsoft.SharePoint.IdentityModel, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Assembly Name="Microsoft.SharePoint, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c"%>
<%@ Page Language="C#" Inherits="MyCustomSignInModule.SignInForm, MyCustomSignInModule, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f2ae721af94bf9e9" MasterPageFile="~/_layouts/15/errorv15.master"%>
<%@ Import Namespace="Microsoft.SharePoint.WebControls" %>
<%@ Register Tagprefix="SharePoint" Namespace="Microsoft.SharePoint.WebControls" Assembly="Microsoft.SharePoint, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Register Tagprefix="Utilities" Namespace="Microsoft.SharePoint.Utilities" Assembly="Microsoft.SharePoint, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<%@ Import Namespace="Microsoft.SharePoint" %>
<%@ Assembly Name="Microsoft.Web.CommandUI, Version=15.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" %>
<asp:Content ContentPlaceHolderId="PlaceHolderPageTitleInTitleArea" runat="server">
<SharePoint:EncodedLiteral runat="server" EncodeMethod="HtmlEncode" Id="ClaimsLogonPageTitleInTitleArea" />
</asp:Content>
<asp:Content ContentPlaceHolderId="PlaceHolderPageTitle" runat="server">
<SharePoint:EncodedLiteral runat="server" EncodeMethod="HtmlEncode" Id="ClaimsFormsPageTitle" />
</asp:Content>
<asp:Content ContentPlaceHolderId="PlaceHolderMain" runat="server">
<SharePoint:EncodedLiteral runat="server" EncodeMethod="HtmlEncode" Id="ClaimsLogonPageMessage" />
<br />
<br />
<SharepointIdentity:LogonSelector ID="ClaimsLogonSelector" runat="server" />
<div id="SslWarning" style="color:red;display:none">
<SharePoint:EncodedLiteral runat="server" EncodeMethod="HtmlEncode" Id="ClaimsFormsPageMessage" />
</div>
<script language="javascript" >
if (document.location.protocol != 'https:') {
var SslWarning = document.getElementById('SslWarning');
SslWarning.style.display = '';
}
</script>
<asp:login id="signInControl" FailureText="<%$Resources:wss,login_pageFailureText%>" runat="server" width="100%">
<layouttemplate>
<asp:label id="FailureText" class="ms-error" runat="server"/>
<table width="100%">
<tr>
<td nowrap="nowrap"><SharePoint:EncodedLiteral runat="server" text="<%$Resources:wss,login_pageUserName%>" EncodeMethod='HtmlEncode'/></td>
<td width="100%"><asp:textbox id="UserName" autocomplete="off" runat="server" class="ms-inputuserfield" width="99%" /></td>
</tr>
<tr>
<td nowrap="nowrap"><SharePoint:EncodedLiteral runat="server" text="<%$Resources:wss,login_pagePassword%>" EncodeMethod='HtmlEncode'/></td>
<td width="100%"><asp:textbox id="password" TextMode="Password" autocomplete="off" runat="server" class="ms-inputuserfield" width="99%"/></td>
</tr>
<tr>
<td colspan="2" align="right"><asp:button id="login" commandname="Login" text="<%$Resources:wss,login_pagetitle%>" runat="server" /></td>
</tr>
<tr>
<td colspan="2"><asp:checkbox id="RememberMe" text="<%$SPHtmlEncodedResources:wss,login_pageRememberMe%>" runat="server" /></td>
</tr>
</table>
</layouttemplate>
</asp:login>
<asp:label id="DebugText" class="ms-error" runat="server"/>
</asp:Content>
MyCustomSignInModule الجمعية
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using Microsoft.IdentityModel.Web;
using Microsoft.SharePoint;
using Microsoft.SharePoint.IdentityModel;
using Microsoft.SharePoint.IdentityModel.Pages;
using Microsoft.SharePoint.Administration;
using Microsoft.SharePoint.Administration.Claims;
using Microsoft.SharePoint.ApplicationRuntime;
using Microsoft.SharePoint.Diagnostics;
using Microsoft.SharePoint.Utilities;
using Microsoft.SharePoint.WebControls;
using System.IdentityModel.Tokens;
using System.Web.Configuration;
namespace MyCustomSignInModule
{
public class SignInForm : FormsSignInPage
{
protected Label DebugText;
private static SPIisSettings _iisSettings;
internal static SPIisSettings iisSettings
{
get
{
if (_iisSettings == null)
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
_iisSettings = SPContext.Current.Site.WebApplication.GetIisSettingsWithFallback(SPContext.Current.Site.Zone);
});
}
return _iisSettings;
}
}
protected void Page_Load(object sender, EventArgs e)
{
HttpRequest request = HttpContext.Current.Request;
bool isWindowsAuth = false;
string username = request["username"];
string password = request["password"];
// If no username is provided, it'll probably be Windows Authentication (NTLMv2 protocol)
if (String.IsNullOrEmpty(username))
{
isWindowsAuth = true;
}
try
{
//SPIisSettings iisSettings = SPContext.Current.Site.WebApplication.IisSettings[SPUrlZone.Default];
if (isWindowsAuth)
{
// Windows Authentication it is
if (iisSettings.UseWindowsClaimsAuthenticationProvider)
{
SPAuthenticationProvider provider = iisSettings.WindowsClaimsAuthenticationProvider;
RedirectToLoginPage(provider); // This should cause automatic sign in
}
}
else
{
// FBA authentication it is.
SPFormsAuthenticationProvider formsClaimsAuthenticationProvider = iisSettings.FormsClaimsAuthenticationProvider;
SecurityToken token = SPSecurityContext.SecurityTokenForFormsAuthentication(new Uri(SPContext.Current.Web.Url), formsClaimsAuthenticationProvider.MembershipProvider, formsClaimsAuthenticationProvider.RoleProvider, username, password, SPFormsAuthenticationOption.PersistentSignInRequest);
if (null != token)
{
EstablishSessionWithToken(token);
base.RedirectToSuccessUrl();
}
}
}
catch (Exception ex)
{
DebugText.Text = ex.ToString();
}
}
// Microsoft.SharePoint.IdentityModel.LogonSelector
private void RedirectToLoginPage(SPAuthenticationProvider provider)
{
string components = HttpContext.Current.Request.Url.GetComponents(UriComponents.Query, UriFormat.SafeUnescaped);
string url = provider.AuthenticationRedirectionUrl.ToString();
if (provider is SPWindowsAuthenticationProvider)
{
components = EnsureUrlSkipsFormsAuthModuleRedirection(components, true);
}
SPUtility.Redirect(url, SPRedirectFlags.Default, this.Context, components);
}
// Microsoft.SharePoint.Utilities.SPUtility
private string EnsureUrlSkipsFormsAuthModuleRedirection
(string url, bool urlIsQueryStringOnly)
{
if (!url.Contains("ReturnUrl="))
{
if (urlIsQueryStringOnly)
{
url = url + (string.IsNullOrEmpty(url) ? "" : "&");
}
else
{
url = url + ((url.IndexOf('?') == -1) ? "?" : "&");
}
url = url + "ReturnUrl=";
}
return url;
}
// Microsoft.SharePoint.IdentityModel.Pages.IdentityModelSignInPageBase
private void EstablishSessionWithToken(SecurityToken securityToken)
{
if (securityToken == null)
{
throw new ArgumentNullException("securityToken");
}
SPFederationAuthenticationModule fam = SPFederationAuthenticationModule.Current;
if (fam == null)
{
throw new InvalidOperationException();
}
fam.SetPrincipalAndWriteSessionToken(securityToken);
}
private SPAuthenticationProvider
GetAuthenticationProvider(string providerName)
{
SPIisSettings iisSettings =
SPContext.Current.Site.WebApplication.IisSettings[SPUrlZone.Default];
foreach (SPAuthenticationProvider currentProvider in
iisSettings.ClaimsAuthenticationProviders)
{
if (currentProvider.DisplayName.ToLower() ==
providerName.ToLower())
{
return currentProvider;
}
}
return null;
}
}
}
عملية
لدي اختبار Sharepoint سبيل المثال تعمل على VM ولكن لا Visual Studio مثبتا وجميع التنمية يتم عن بعد.العملية الحالية أتابع ؛
- بناء الفئة C# مكتبة (وهذا سوف يكون
MyCustomSignInModule.Dll
) - التوقيع
MyCustomSignInModule.Dll
بحيث يمكن وضعها في VM GAC. - تسجيل
MyCustomSignInModule.Dll
في GAC على VM سبيل المثال. - حفظ
SignInForm.aspx
في%CommonProgramFiles%\Microsoft Shared\Web Server Extensions\14\TEMPLATE\LAYOUTS\
وهو ما يعادل<SharePointSiteRoot>/_layouts/
الدليل الظاهري في IIS. - في "إدارة SharePoint المركزية" مجموعة موقع مخصص صفحة تسجيل الدخول إلى الصفحة الخاصة بي
~/_layouts/SignInForm.aspx
. - إعادة تعيين IIS باستخدام
iisreset
. - اختبار الوصول إلى موقع SharePoint (هذا هو المكان الذي يقع).
المشكلة
إذا لم يكن ذلك واضحا الخطأ ؛
System.NullReferenceException: Object reference not set to an instance of an object. at
MyCustomSignInModule.SignInForm.b__0() at
Microsoft.SharePoint.SPSecurity.<>c__DisplayClass5.b__3() at
Microsoft.SharePoint.Utilities.SecurityContext.RunAsProcess(CodeToRunElevated secureCode) at
Microsoft.SharePoint.SPSecurity.RunWithElevatedPrivileges(WaitCallback secureCode, Object param) at
Microsoft.SharePoint.SPSecurity.RunWithElevatedPrivileges(CodeToRunElevated secureCode) at MyCustomSignInModule.SignInForm.get_iisSettings() at
MyCustomSignInModule.SignInForm.Page_Load(Object sender, EventArgs e)
SPContext.الحالي باطل لماذا ؟
على NullReferenceException
بسبب SPContext.Current
يتم null, ولكن لا أستطيع تجريب لماذا انها فارغة ولا يوجد كمية من المواد لقد نظرت حتى الآن أدى إلى يساعدني في حل هذه.أتمنى من خلال نشر حياتي العملية هنا شخص ما قد تكون قادرة على نقطة لي ما أنا في عداد المفقودين أو به خطأ.
المحلول
أخيرا حصلت على الجزء السفلي من ما كان يسبب المشكلة, أولا أود أن أشكر كل من @MdMazzotti و @هيو الخشب عن استمرار المساعدة.
في النهاية أنا تعثرت على الإصلاح التي تحولت إلى أن تكون جزئيا بسبب الطريقة التي تم بناء الموقع.في حالتي تم بناء الموقع مثل الموقع الفرعي في SharePoint ، لأي سبب من الأسباب وهذا يعني أن هناك أي مجموعة الموقع في جذر موقع SharePoint الذي كان سبب Null
SPContext
في قانون بلدي.
بعد إضافة الموقع الجذر جمع بلدي رمز بدأ العمل كما هو متوقع.
نصائح أخرى
أنا فقط أخمن هنا, ولكن هنا هي بعض الأشياء التي أعتقد أنها يمكن أن تساعد.
هذا إضافة جافا سكريبت رمز علامة مخصصة في صفحة (قبل إذا-البيان):
SP.SOD.executeFunc('SP.js', 'SP.ClientContext');
يمكنك أيضا أن تضيف هذه جافا سكريبت على الصفحة الخاصة بك لاختبار ما إذا كان يعمل أم لا ، باستخدام وحدة التحكم:
var clientContext = new SP.ClientContext.get_current();
console.log(clientContext);
إذا تعود شيئا ، ثم علينا التقدم!إذا أنا يجب أن أواصل البحث ، حيث أجد السؤال الخاص بك مثيرة للاهتمام.
تحرير
بدلا من استخدام هذا تعليمات برمجية من جانب الخادم:
if (_iisSettings == null)
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
_iisSettings = SPContext.Current.Site.WebApplication.GetIisSettingsWithFallback(SPContext.Current.Site.Zone);
});
}
return _iisSettings;
حاول استخدام هذا بدلا من ذلك:
if (_iisSettings == null)
{
SPSecurity.RunWithElevatedPrivileges(delegate()
{
_iisSettings = Microsoft.SharePoint.SPContext.Current.Site.WebApplication.GetIisSettingsWithFallback(Microsoft.SharePoint.SPContext.Current.Site.Zone);
});
}
return _iisSettings;
بحثت حولي و لاحظت ذلك في بعض أمثلة التعليمات البرمجية التي واجهت ، _iisSettings مختلفة من يدكم.ولعل هذا هو السبب الخاص بك SPContext.الحالي باطل?
يرجى التحقق من هذه الإجابة:https://stackoverflow.com/questions/5081251/how-can-this-throw-a-nullreferenceexception
SPContext.الحالي لا يعمل تحت امتيازات مرتفعة ، لذلك عليك أن كتابة مثل في الجواب أعلاه.
يمكنك مراجعة هذه المقالة MSDN: http://msdn.microsoft.com/en-us/library/office/ms468609(v=المكتب.14).aspx
أعتقد لأن كنت تستخدم C# مكتبة فئة المشروع في Visual studio, أنت لست في سياق شبكة الإنترنت و لا يمكن استخدام SPContext.الحالية كما هو موضح في المقالة MSDN أعلاه.